13Poker by gametower unlimited gems v0.4版本的 MD5 值为:51324fc0f195c34821074948ab266846

以下内容为反编译后的 MRaid.java 源代码,内容仅作参考


package com.millennialmedia.android;

import android.content.Context;
import android.content.SharedPreferences;
import android.net.Uri;
import android.text.TextUtils;
import com.millennialmedia.android.MMSDK;
import com.millennialmedia.android.Utils;
import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStream;
import java.lang.ref.WeakReference;
import java.net.MalformedURLException;
import java.security.MessageDigest;
import java.util.Date;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.impl.client.DefaultHttpClient;
public class MRaid {
    private static final String KEY_MMJS_URL = "KEY_MMJS_URL";
    private static final String MMJS_1_4_PART1 = "LyoqCiogTWlsbGVubmlhbCBNZWRpYSBKUyBMaWJyYXJ5IChNTS5qcykKKiBDb3B5cmlnaHQgMjAxMC0yMDEzLCBNaWxsZW5uaWFsIE1lZGlhCioKKiBWZXJzaW9uOiAxLjQKKiBCdWlsdCBvbiBNb24gSnVuIDI0IDIwMTMgMTQ6MDg6MTEgR01ULTA3MDAgKFBEVCkuCiovCgovLyBHZW5lcmF0ZWQgYnkgQ29mZmVlU2NyaXB0IDEuNi4yCnZhciBNTUFwcFN0b3JlLCBNTUJhbm5lciwgTU1CcmFuZCwgTU1CcmlkZ2VPYmplY3QsIE1NQ2FjaGVkVmlkZW8sIE1NQ2FsZW5kYXIsIE1NQ29tbWFuZCwgTU1EZXZpY2UsIE1NRmlsZU1hbmFnZXIsIE1NSW5saW5lVmlkZW8sIE1NSW50ZXJzdGl0aWFsLCBNTUpTLCBNTUpTVXRpbHMsIE1NTGlzdGVuZXJNYW5hZ2VyLCBNTU1lZGlhLCBNTU1pY3JvcGhvbmUsIE1NTm90aWZpY2F0aW9uLCBNTVBhc3Nib29rLCBNTVBhc3RlYm9hcmQsIE1NU0RLSW50ZXJmYWNlLCBNTVNvY2lhbCwgTU1TcGVlY2hraXQsIE1SQUlELCBfcmVmLCBfcmVmMSwgX3JlZjEwLCBfcmVmMTEsIF9yZWYxMiwgX3JlZjEzLCBfcmVmMTQsIF9yZWYxNSwgX3JlZjIsIF9yZWYzLCBfcmVmNCwgX3JlZjUsIF9yZWY2LCBfcmVmNywgX3JlZjgsIF9yZWY5LAogIF9faGFzUHJvcCA9IHt9Lmhhc093blByb3BlcnR5LAogIF9fZXh0ZW5kcyA9IGZ1bmN0aW9uKGNoaWxkLCBwYXJlbnQpIHsgZm9yICh2YXIga2V5IGluIHBhcmVudCkgeyBpZiAoX19oYXNQcm9wLmNhbGwocGFyZW50LCBrZXkpKSBjaGlsZFtrZXldID0gcGFyZW50W2tleV07IH0gZnVuY3Rpb24gY3RvcigpIHsgdGhpcy5jb25zdHJ1Y3RvciA9IGNoaWxkOyB9IGN0b3IucHJvdG90eXBlID0gcGFyZW50LnByb3RvdHlwZTsgY2hpbGQucHJvdG90eXBlID0gbmV3IGN0b3IoKTsgY2hpbGQuX19zdXBlcl9fID0gcGFyZW50LnByb3RvdHlwZTsgcmV0dXJuIGNoaWxkOyB9OwoKU3RyaW5nLnByb3RvdHlwZS50cmltID0gZnVuY3Rpb24oKSB7CiAgcmV0dXJuIHRoaXMucmVwbGFjZShSZWdFeHAoIl5cXHMrfFxccyskIiwgImciKSwgIiIpOwp9OwoKU3RyaW5nLnByb3RvdHlwZS50aXRsZUNhc2UgPSBmdW5jdGlvbigpIHsKICByZXR1cm4gdGhpcy5yZXBsYWNlKFJlZ0V4cCgiXFx3XFxTKiIsICJnIiksIGZ1bmN0aW9uKHN0cikgewogICAgcmV0dXJuIHN0ci5jaGFyQXQoMCkudG9VcHBlckNhc2UoKS5jb25jYXQoc3RyLnN1YnN0cigxKS50b0xvd2VyQ2FzZSgpKTsKICB9KTsKfTsKCmlmICh0eXBlb2YgTU1KUyA9PT0gdHlwZW9mIHZvaWQgMCkgewogIE1NSlNVdGlscyA9IChmdW5jdGlvbigpIHsKICAgIGZ1bmN0aW9uIE1NSlNVdGlscygpIHt9CgogICAgTU1KU1V0aWxzLmlvc192ZXJzaW9uID0gbnVsbDsKCiAgICBNTUpTVXRpbHMucGxhdGZvcm0gPSBudWxsOwoKICAgIE1NSlNVdGlscy5zZGtfdmVyc2lvbiA9IG51bGw7CgogICAgTU1KU1V0aWxzLnBhcmFtcyA9IG51bGw7CgogICAgTU1KU1V0aWxzLmlzQnJpZGdlRW5hYmxlZCA9IGZ1bmN0aW9uKCkgewogICAgICBpZiAoTU1EZXZpY2UucmVhZHlTdGF0ZSAhPT0gInVua25vd24iKSB7CiAgICAgICAgcmV0dXJuIHRydWU7CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfTsKCiAgICBNTUpTVXRpbHMuaXNQcmU0NiA9IGZ1bmN0aW9uKGEpIHsKICAgICAgaWYgKHRoaXMuaXNCcmlkZ2VFbmFibGVkKCkgPT09IHRydWUpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgaWYgKGEgPT0gbnVsbCkgewogICAgICAgIHJldHVybiB0cnVlOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLnVuZGVyVmVyc2lvbihhLCAiNC42LjAiKTsKICAgIH07CgogICAgTU1KU1V0aWxzLnVuZGVyVmVyc2lvbiA9IGZ1bmN0aW9uKHZlcnNpb25TdHJpbmcsIG1pblZlcnNpb24pIHsKICAgICAgdmFyIGksIHJlcywgcmVzdWx0LCB2MSwgdjI7CgogICAgICBpZiAodmVyc2lvblN0cmluZyA9PSBudWxsKSB7CiAgICAgICAgcmV0dXJuIGZhbHNlOwogICAgICB9CiAgICAgIHYxID0gdmVyc2lvblN0cmluZy5zcGxpdCgiLiIpOwogICAgICB2MiA9IG1pblZlcnNpb24uc3BsaXQoIi4iKTsKICAgICAgaSA9IDA7CiAgICAgIHJlc3VsdCA9IDA7CiAgICAgIHdoaWxlIChpIDwgTWF0aC5taW4odjEubGVuZ3RoLCB2Mi5sZW5ndGgpKSB7CiAgICAgICAgcmVzID0gdjFbaV0gLSB2MltpXTsKICAgICAgICBpZiAocmVzICE9PSAwKSB7CiAgICAgICAgICByZXN1bHQgPSByZXM7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgICAgaSsrOwogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQgPCAwOwogICAgfTsKCiAgICBNTUpTVXRpbHMuaXNWZXJzaW9uID0gZnVuY3Rpb24odmVyc2lvblN0cmluZykgewogICAgICB2YXIgaSwgcmVzLCByZXN1bHQsIHYxLCB2MjsKCiAgICAgIGlmICh2ZXJzaW9uU3RyaW5nID09IG51bGwpIHsKICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgIH0KICAgICAgdjEgPSB2ZXJzaW9uU3RyaW5nLnNwbGl0KCIuIik7CiAgICAgIHYyID0gdGhpcy5zZGtWZXJzaW9uKCkuc3BsaXQoIi4iKTsKICAgICAgaSA9IDA7CiAgICAgIHJlc3VsdCA9IDA7CiAgICAgIHdoaWxlIChpIDwgTWF0aC5taW4odjEubGVuZ3RoLCB2Mi5sZW5ndGgpKSB7CiAgICAgICAgcmVzID0gdjFbaV0gLSB2MltpXTsKICAgICAgICBpZiAocmVzICE9PSAwKSB7CiAgICAgICAgICByZXN1bHQgPSByZXM7CiAgICAgICAgICBicmVhazsKICAgICAgICB9CiAgICAgICAgaSsrOwogICAgICB9CiAgICAgIHJldHVybiByZXN1bHQgPT09IDA7CiAgICB9OwoKICAgIE1NSlNVdGlscy5pc0lPUyA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gdGhpcy5nZXRQbGF0Zm9ybSgpID09PSAiaW9zIjsKICAgIH07CgogICAgTU1KU1V0aWxzLmlzV2luZG93cyA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gdGhpcy5nZXRQbGF0Zm9ybSgpID09PSAid2luZG93cyI7CiAgICB9OwoKICAgIE1NSlNVdGlscy5pc0JsYWNrQmVycnkgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIHRoaXMuZ2V0UGxhdGZvcm0oKSA9PT0gImJsYWNrYmVycnkiOwogICAgfTsKCiAgICBNTUpTVXRpbHMuaXNBbmRyb2lkID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLmdldFBsYXRmb3JtKCkgPT09ICJhbmRyb2lkIjsKICAgIH07CgogICAgTU1KU1V0aWxzLmdldFBsYXRmb3JtID0gZnVuY3Rpb24oKSB7CiAgICAgIGlmICh0aGlzLnBsYXRmb3JtICE9IG51bGwpIHsKICAgICAgICByZXR1cm4gdGhpcy5wbGF0Zm9ybTsKICAgICAgfQogICAgICBpZiAobmF2aWdhdG9yLnBsYXRmb3JtLm1hdGNoKC8oQW5kcm9pZCkvKSAhPSBudWxsKSB7CiAgICAgICAgdGhpcy5wbGF0Zm9ybSA9ICJhbmRyb2lkIjsKICAgICAgfSBlbHNlIGlmIChuYXZpZ2F0b3IucGxhdGZvcm0ubWF0Y2goL14oaVBhZHxpUG9kfGlQaG9uZSkvKSAhPSBudWxsKSB7CiAgICAgICAgdGhpcy5wbGF0Zm9ybSA9ICJpb3MiOwogICAgICB9IGVsc2UgewogICAgICAgIHRoaXMucGxhdGZvcm0gPSAiYW5kcm9pZCI7CiAgICAgIH0KICAgICAgcmV0dXJuIHRoaXMucGxhdGZvcm07CiAgICB9OwoKICAgIE1NSlNVdGlscy5zZGtWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBtbWlzZGssIHBhcmFtczsKCiAgICAgIGlmICh0aGlzLnNka192ZXJzaW9uICE9IG51bGwpIHsKICAgICAgICByZXR1cm4gdGhpcy5zZGtfdmVyc2lvbjsKICAgICAgfQogICAgICBpZiAoTU1KUy5zZGtWZXJzaW9uICE9IG51bGwpIHsKICAgICAgICB0aGlzLnNka192ZXJpc29uID0gTU1KUy5zZGtWZXJzaW9uOwogICAgICAgIHJldHVybiB0aGlzLnNka192ZXJzaW9uOwogICAgICB9CiAgICAgIHBhcmFtcyA9IHRoaXMuZ2V0UGFyYW1zKCk7CiAgICAgIGlmIChwYXJhbXNbJ3Nka3ZlcnNpb24nXSAhPSBudWxsKSB7CiAgICAgICAgbW1pc2RrID0gcGFyYW1zWydzZGt2ZXJzaW9uJ10uc3BsaXQoJy0nKTsKICAgICAgICB0aGlzLnNka192ZXJzaW9uID0gbW1pc2RrWzBdOwogICAgICAgIHJldHVybiB0aGlzLnNka192ZXJzaW9uOwogICAgICB9CiAgICAgIHJldHVybiBudWxsOwogICAgfTsKCiAgICBNTUpTVXRpbHMuc2ltdWxhdGVSZWRpcmVjdCA9IGZ1bmN0aW9uKHVybCkgewogICAgICB2YXIgZXZlbnRGaXJlLCBsaW5rVGFnOwoKICAgICAgbGlua1RhZyA9IGRvY3VtZW50LmNyZWF0ZUVsZW1lbnQoImEiKTsKICAgICAgbGlua1RhZy5pZCA9ICJtbV9zaW11bGF0ZUxpbmsiOwogICAgICBsaW5rVGFnLnNldEF0dHJpYnV0ZSgiaHJlZiIsIHVybCk7CiAgICAgIGxpbmtUYWcuc2V0QXR0cmlidXRlKCJzdHlsZSIsICJvcGFjaXR5OjAiKTsKICAgICAgZG9jdW1lbnQuYm9keS5hcHBlbmRDaGlsZChsaW5rVGFnKTsKICAgICAgZXZlbnRGaXJlID0gZnVuY3Rpb24oZWwsIGV0eXBlKSB7CiAgICAgICAgdmFyIGV2T2JqOwoKICAgICAgICBpZiAoZWwuZmlyZUV2ZW50KSB7CiAgICAgICAgICByZXR1cm4gZWwuZmlyZUV2ZW50KCJvbiIgKyBldHlwZSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIGV2T2JqID0gZG9jdW1lbnQuY3JlYXRlRXZlbnQoIkV2ZW50cyIpOwogICAgICAgICAgZXZPYmouaW5pdEV2ZW50KGV0eXBlLCB0cnVlLCBmYWxzZSk7CiAgICAgICAgICByZXR1cm4gZWwuZGlzcGF0Y2hFdmVudChldk9iaik7CiAgICAgICAgfQogICAgICB9OwogICAgICByZXR1cm4gd2luZG93LnNldFRpbWVvdXQoKGZ1bmN0aW9uKCkgewogICAgICAgIHZhciBlbGVtZW50OwoKICAgICAgICBlbGVtZW50ID0gbGlua1RhZzsKICAgICAgICByZXR1cm4gZXZlbnRGaXJlKGxpbmtUYWcsICJjbGljayIpOwogICAgICB9KSwgMSk7CiAgICB9OwoKICAgIE1NSlNVdGlscy5tb2REdXJhdGlvbiA9IGZ1bmN0aW9uKGR1cmF0aW9uKSB7CiAgICAgIGlmICghdGhpcy5pc0FuZHJvaWQoKSkgewogICAgICAgIHJldHVybiBkdXJhdGlvbjsKICAgICAgfQogICAgICBpZiAoZHVyYXRpb24gPCAxMDApIHsKICAgICAgICByZXR1cm4gZHVyYXRpb24gKiAxMDAwOwogICAgICB9IGVsc2UgewogICAgICAgIHJldHVybiBkdXJhdGlvbjsKICAgICAgfQogICAgfTsKCiAgICBNTUpTVXRpbHMuZ2V0UGFyYW1zID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBuLCBuYW1lLCBwYWlyLCBwYXJhbXMsIHFzLCB2YWx1ZSwgX2ksIF9sZW4sIF9yZWYsIF9yZWYxOwoKICAgICAgaWYgKHRoaXMucGFyYW1zICE9IG51bGwpIHsKICAgICAgICByZXR1cm4gdGhpcy5wYXJhbXM7CiAgICAgIH0KICAgICAgcGFyYW1zID0ge307CiAgICAgIHFzID0gd2luZG93LmxvY2F0aW9uLnNlYXJjaC5zdWJzdHJpbmcoMSk7CiAgICAgIGlmIChxcy5sZW5ndGgpIHsKICAgICAgICBfcmVmID0gKGZ1bmN0aW9uKCkgewogICAgICAgICAgdmFyIF9qLCBfbGVuLCBfcmVmLCBfcmVzdWx0czsKCiAgICAgICAgICBfcmVmID0gcXMuc3BsaXQoJyYnKTsKICAgICAgICAgIF9yZXN1bHRzID0gW107CiAgICAgICAgICBmb3IgKF9qID0gMCwgX2xlbiA9IF9yZWYubGVuZ3RoOyBfaiA8IF9sZW47IF9qKyspIHsKICAgICAgICAgICAgcGFpciA9IF9yZWZbX2pdOwogICAgICAgICAgICBfcmVzdWx0cy5wdXNoKHBhaXIuc3BsaXQoJz0nKSk7CiAgICAgICAgICB9CiAgICAgICAgICByZXR1cm4gX3Jlc3VsdHM7CiAgICAgICAgfSkoKTsKICAgICAgICBmb3IgKF9pID0gMCwgX2xlbiA9IF9yZWYubGVuZ3RoOyBfaSA8IF9sZW47IF9pKyspIHsKICAgICAgICAgIF9yZWYxID0gX3JlZltfaV0sIG5hbWUgPSBfcmVmMVswXSwgdmFsdWUgPSBfcmVmMVsxXTsKICAgICAgICAgIG4gPSBuYW1lLnJlcGxhY2UoIm1tXyIsICIiKTsKICAgICAgICAgIGlmICh2YWx1ZSAhPSBudWxsKSB7CiAgICAgICAgICAgIHBhcmFtc1tuXSA9IHZhbHVlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICB0aGlzLnBhcmFtcyA9IHBhcmFtczsKICAgICAgcmV0dXJuIHRoaXMucGFyYW1zOwogICAgfTsKCiAgICBNTUpTVXRpbHMuY29uc29sZUxvZyA9IGZ1bmN0aW9uKF9tc2csIF91c2VBbGVydCkgewogICAgICBpZiAoX3VzZUFsZXJ0ID09IG51bGwpIHsKICAgICAgICBfdXNlQWxlcnQgPSBmYWxzZTsKICAgICAgfQogICAgICBNTUpTLmV2ZW50VHJhY2tpbmcucHVzaChfbXNnKTsKICAgICAgaWYgKHRoaXMuaXNBbmRyb2lkKCkpIHsKICAgICAgICBpZiAod2luZG93LmNvbnNvbGUgIT0gbnVsbCkgewogICAgICAgICAgd2luZG93LmNvbnNvbGUubG9nKF9tc2cpOwogICAgICAgIH0KICAgICAgfSBlbHNlIGlmICh0aGlzLmlzV2luZG93cygpKSB7CiAgICAgICAgd2luZG93LmV4dGVybmFsLm5vdGlmeShfbXNnKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBpZiAod2luZG93LmNvbnNvbGUgIT0gbnVsbCkgewogICAgICAgICAgd2luZG93LmNvbnNvbGUubG9nKF9tc2cpOwogICAgICAgIH0KICAgICAgICBpZiAoX3VzZUFsZXJ0KSB7CiAgICAgICAgICBhbGVydChfbXNnKTsKICAgICAgICB9CiAgICAgIH0KICAgICAgcmV0dXJuIGZhbHNlOwogICAgfTsKCiAgICBNTUpTVXRpbHMuaU9TVmVyc2lvbiA9IGZ1bmN0aW9uKCkgewogICAgICB2YXIgX3Y7CgogICAgICBpZiAodGhpcy5pb3NfdmVyc2lvbikgewogICAgICAgIHJldHVybiB0aGlzLmlvc192ZXJzaW9uOwogICAgICB9CiAgICAgIF92ID0gbmF2aWdhdG9yLmFwcFZlcnNpb24uc3BsaXQoJyBPUyAnKVsxXTsKICAgICAgX3YgPSBfdi5zcGxpdCgnICcpWzBdLnRyaW0oKS5zcGxpdCgnXycpOwogICAgICBfdi5zcGxpY2UoMSwgMCwgJy4nKTsKICAgICAgcmV0dXJuIHRoaXMuaW9zX3ZlcnNpb24gPSBwYXJzZUZsb2F0KF92LmpvaW4oJycpKTsKICAgIH07CgogICAgTU1KU1V0aWxzLmdldExvY2F0aW9uID0gZnVuY3Rpb24oZnVuYywgZXJyb3IpIHsKICAgICAgaWYgKG5hdmlnYXRvci5nZW9sb2NhdGlvbikgewogICAgICAgIHJldHVybiBuYXZpZ2F0b3IuZ2VvbG9jYXRpb24uZ2V0Q3VycmVudFBvc2l0aW9uKGZ1bmMsIGVycm9yLCB7CiAgICAgICAgICBlbmFibGVIaWdoQWNjdXJhY3k6IHRydWUKICAgICAgICB9KTsKICAgICAgfSBlbHNlIHsKICAgICAgICByZXR1cm4gZXJyb3IoewogICAgICAgICAgY29kZTogOTkKICAgICAgICB9KTsKICAgICAgfQogICAgfTsKCiAgICBNTUpTVXRpbHMubGlzdGVuRm9yQnJvd3NlclJlYWR5ID0gZnVuY3Rpb24oZnVuYykgewogICAgICBpZiAodGhpcy5pc1dpbmRvd3MoKSkgewogICAgICAgIHJldHVybiBkb2N1bWVudC5hdHRhY2hFdmVudCgib25yZWFkeXN0YXRlY2hhbmdlIiwgZnVuYyk7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIGRvY3VtZW50LmFkZEV2ZW50TGlzdGVuZXIoIkRPTUNvbnRlbnRMb2FkZWQiLCBmdW5jLCBmYWxzZSk7CiAgICAgIH0KICAgIH07CgogICAgTU1KU1V0aWxzLnBvc3RFdmVudCA9IGZ1bmN0aW9uKGV2ZW50KSB7CiAgICAgIHZhciBldk9iajsKCiAgICAgIGlmIChkb2N1bWVudC5jcmVhdGVFdmVudCkgewogICAgICAgIGV2T2JqID0gZG9jdW1lbnQuY3JlYXRlRXZlbnQoIkV2ZW50Iik7CiAgICAgICAgZXZPYmouaW5pdEV2ZW50KGV2ZW50LCB0cnVlLCB0cnVlKTsKICAgICAgICByZXR1cm4gd2luZG93LmRvY3VtZW50LmRpc3BhdGNoRXZlbnQoZXZPYmopOwogICAgICB9IGVsc2UgaWYgKGRvY3VtZW50LmNyZWF0ZUV2ZW50T2JqZWN0IHx8IHRoaXMuaXNXaW5kb3dzKCkpIHsKICAgICAgICByZXR1cm4gZG9jdW1lbnQuYm9keS5maXJlRXZlbnQoIm9uIiArIGV2ZW50KTsKICAgICAgfQogICAgfTsKCiAgICBNTUpTVXRpbHMub2Zmc2V0ID0gZnVuY3Rpb24oX2VsKSB7CiAgICAgIHZhciBjb29yZHMsIHBfY29vcmRzOwoKICAgICAgY29vcmRzID0gW19lbC5vZmZzZXRMZWZ0LCBfZWwub2Zmc2V0VG9wXTsKICAgICAgaWYgKF9lbC5vZmZzZXRQYXJlbnQgIT0gbnVsbCkgewogICAgICAgIHBfY29vcmRzID0gdGhpcy5vZmZzZXQoX2VsLm9mZnNldFBhcmVudCk7CiAgICAgICAgY29vcmRzWzBdICs9IHBfY29vcmRzWzBdOwogICAgICAgIGNvb3Jkc1sxXSArPSBwX2Nvb3Jkc1sxXTsKICAgICAgfQogICAgICByZXR1cm4gY29vcmRzOwogICAgfTsKCiAgICByZXR1cm4gTU1KU1V0aWxzOwoKICB9KSgpOwogIE1NSlMgPSAoZnVuY3Rpb24oKSB7CiAgICBmdW5jdGlvbiBNTUpTKCkge30KCiAgICBNTUpTLlZFUlNJT04gPSAiMS4zIjsKCiAgICBNTUpTLmNvbW1hbmRRdWV1ZSA9IFtdOwoKICAgIE1NSlMuYW5kcm9pZEludGVyZmFjZSA9IHdpbmRvd1snaW50ZXJmYWNlJ107CgogICAgTU1KUy51dGlscyA9IE1NSlNVdGlsczsKCiAgICBNTUpTLnNka1JlYWR5ID0gZmFsc2U7CgogICAgTU1KUy5leGVjdXRpbmdDb21tYW5kID0gZmFsc2U7CgogICAgTU1KUy5leGVjdXRpbmdDb21tYW5kRGVsYXkgPSAwOwoKICAgIE1NSlMucGFyYW1zID0gbnVsbDsKCiAgICBNTUpTLnBsYXRmb3JtID0gbnVsbDsKCiAgICBNTUpTLmNhbGxiYWNrcyA9IHt9OwoKICAgIE1NSlMubGlzdGVuZXJzID0ge307CgogICAgTU1KUy5zZGtWZXJzaW9uID0gbnVsbDsKCiAgICBNTUpTLm9wZW5DYWxsZWQgPSBmYWxzZTsKCiAgICBNTUpTLlRZUEVfU1RSSU5HID0gdHlwZW9mICIiOwoKICAgIE1NSlMuVFlQRV9PQkpFQ1QgPSB0eXBlb2YgW107CgogICAgTU1KUy5UWVBFX0ZVTkNUSU9OID0gdHlwZW9mIGZ1bmN0aW9uKCkge307CgogICAgTU1KUy5UWVBFX05VTUJFUiA9IHR5cGVvZiAwOwoKICAgIE1NSlMuVFlQRV9VTkRFRklORUQgPSAidW5kZWZpbmVkIjsKCiAgICBNTUpTLmV2ZW50VHJhY2tpbmcgPSBbXTsKCiAgICBNTUpTLnNldEV4ZWN1dGluZ0NvbW1hbmQgPSBmdW5jdGlvbihfZXhlY3V0aW5nLCBfdGltZSkgewogICAgICBpZiAoX3RpbWUgPT0gbnVsbCkgewogICAgICAgIF90aW1lID0gMTAwMDA7CiAgICAgIH0KICAgICAgdGhpcy5sb2dDYWxsc3RhY2soKTsKICAgICAgcmV0dXJuIHRoaXMuZXhlY3V0aW5nQ29tbWFuZCA9IF9leGVjdXRpbmc7CiAgICB9OwoKICAgIE1NSlMubG9nQ2FsbHN0YWNrID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBjYWxsc3RhY2ssIGN1cnJlbnRGdW5jdGlvbiwgZm4sIGZuYW1lOwoKICAgICAgY2FsbHN0YWNrID0gW107CiAgICAgIGN1cnJlbnRGdW5jdGlvbiA9IGFyZ3VtZW50cy5jYWxsZWUuY2FsbGVyOwogICAgICB3aGlsZSAoY3VycmVudEZ1bmN0aW9uKSB7CiAgICAgICAgZm4gPSBjdXJyZW50RnVuY3Rpb24udG9TdHJpbmcoKTsKICAgICAgICBmbmFtZSA9IGZuLnN1YnN0cmluZyhmbi5pbmRleE9mKCJmdW5jdGlvbiIpICsgOCwgZm4uaW5kZXhPZigiIikpIHx8ICJhbm9ueW1vdXMiOwogICAgICAgIGNhbGxzdGFjay5wdXNoKGZuYW1lKTsKICAgICAgICBjdXJyZW50RnVuY3Rpb24gPSBjdXJyZW50RnVuY3Rpb24uY2FsbGVyOwogICAgICB9CiAgICAgIHJldHVybiBNTUpTLnV0aWxzLmNvbnNvbGVMb2coY2FsbHN0YWNrKTsKICAgIH07CgogICAgTU1KUy5kZWJ1ZyA9IGZ1bmN0aW9uKCkgewogICAgICB2YXIgdG9Mb2c7CgogICAgICB0b0xvZyA9IHRoaXMuZXZlbnRUcmFja2luZy5qb2luKCJcbiIpOwogICAgICBjb25zb2xlLmxvZyh0b0xvZyk7CiAgICAgIHJldHVybiB0cnVlOwogICAgfTsKCiAgICBNTUpTLnNldFNES1ZlcnNpb24gPSBmdW5jdGlvbih2ZXJzaW9uKSB7CiAgICAgIHJldHVybiB0aGlzLnNka1ZlcnNpb24gPSB2ZXJzaW9uOwogICAgfTsKCiAgICBNTUpTLm1tc2RrT3BlbkZ1bmN0aW9uID0gbnVsbDsKCiAgICBNTUpTLnNob3VsZE9wZW5XYXNDYWxsZWQgPSBmYWxzZTsKCiAgICBNTUpTLnNldHVwT3ZlcmxheSA9IGZ1bmN0aW9uKHVybCwgcGFyYW1zKSB7CiAgICAgIGlmIChwYXJhbXMgPT0gbnVsbCkgewogICAgICAgIHBhcmFtcyA9IHt9OwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLm9wZW4odXJsLCBwYXJhbXMsIGZhbHNlKTsKICAgIH07CgogICAgTU1KUy5vcGVuID0gZnVuY3Rpb24odXJsLCBwYXJhbXMsIGF1dG9FeHBhbmQpIHsKICAgICAgaWYgKHBhcmFtcyA9PSBudWxsKSB7CiAgICAgICAgcGFyYW1zID0ge307CiAgICAgIH0KICAgICAgaWYgKGF1dG9FeHBhbmQgPT0gbnVsbCkgewogICAgICAgIGF1dG9FeHBhbmQgPSB0cnVlOwogICAgICB9CiAgICAgIG1yYWlkLnNldEV4cGFuZFByb3BlcnRpZXMocGFyYW1zKTsKICAgICAgcmV0dXJuIG1yYWlkLmV4cGFuZCh1cmwpOwogICAgfTsKCiAgICBNTUpTLmNsb3NlID0gZnVuY3Rpb24oZHVyYXRpb24pIHsKICAgICAgdmFyIG1vZER1cmF0aW9uOwoKICAgICAgaWYgKGR1cmF0aW9uID09IG51bGwpIHsKICAgICAgICBkdXJhdGlvbiA9IDA7CiAgICAgIH0KICAgICAgbW9kRHVyYXRpb24gPSBmdW5jdGlvbihkdXJhdGlvbikgewogICAgICAgIGlmIChkdXJhdGlvbiA8IDEwMCkgewogICAgICAgICAgcmV0dXJuIGR1cmF0aW9uICogMTAwMDsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuIGR1cmF0aW9uOwogICAgICAgIH0KICAgICAgfTsKICAgICAgcmV0dXJuIHNldFRpbWVvdXQoZnVuY3Rpb24oKSB7CiAgICAgICAgcmV0dXJuIE1NSlMuaW50ZXJzdGl0aWFsLmNsb3NlKCk7CiAgICAgIH0sIG1vZER1cmF0aW9uKGR1cmF0aW9uKSk7CiAgICB9OwoKICAgIE1NSlMub3BlbkV4dGVybmFsID0gZnVuY3Rpb24odXJsKSB7CiAgICAgIGlmICh0aGlzLnV0aWxzLmlzQnJpZGdlRW5hYmxlZCgpKSB7CiAgICAgICAgcmV0dXJuIE1NRGV2aWNlLm9wZW5VcmwodXJsKTsKICAgICAgfSBlbHNlIHsKICAgICAgICBpZiAodGhpcy51dGlscy5pc0lPUygpKSB7CiAgICAgICAgICByZXR1cm4gd2luZG93LmxvY2F0aW9uID0gIm1tYnJvd3Nlcjo6Ly8iICsgdXJsOwogICAgICAgIH0gZWxzZSB7CiAgICAgICAgICByZXR1cm4gd2luZG93LmxvY2F0aW9uID0gIm1tYnJvd3NlcjovLyIgKyB1cmw7CiAgICAgICAgfQogICAgICB9CiAgICB9OwoKICAgIE1NSlMucmVtb3ZlRXZlbnRMaXN0ZW5lciA9IGZ1bmN0aW9uKGV2ZW50LCBsaXN0ZW5lcikgewogICAgICByZXR1cm4gZGVsZXRlIHRoaXMubGlzdGVuZXJzW2V2ZW50XTsKICAgIH07CgogICAgTU1KUy5hZGRFdmVudExpc3RlbmVyID0gZnVuY3Rpb24oZXZlbnQsIGxpc3RlbmVyKSB7CiAgICAgIHJldHVybiB0aGlzLmxpc3RlbmVyc1tldmVudF0gPSBsaXN0ZW5lcjsKICAgIH07CgogICAgLyogSlM8PT5TREsgQnJpZGdlCiAgICAqLwoKCiAgICBNTUpTLmVucXVldWVDb21tYW5kID0gZnVuY3Rpb24oY29tbWFuZCkgewogICAgICB0aGlzLmNvbW1hbmRRdWV1ZS5wdXNoKGNvbW1hbmQpOwogICAgICByZXR1cm4gdGhpcy51dGlscy5jb25zb2xlTG9nKCJjb21tYW5kUXVldWUgIiArIE1NSlMuY29tbWFuZFF1ZXVlKTsKICAgIH07CgogICAgTU1KUy5jYWxsYmFjayA9IGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgIHZhciBrbGFzcywga2xhc3NGdW5jdGlvbiwgbWV0aG9kLCByZXNwb25zZV9kYXRhLCByZXN1bHQ7CgogICAgICByZXN1bHQgPSByZXNwb25zZVsncmVzdWx0J107CiAgICAgIG1ldGhvZCA9IHJlc3BvbnNlWydjYWxsJ107CiAgICAgIHJlc3BvbnNlX2RhdGEgPSByZXNwb25zZVsncmVzcG9uc2UnXTsKICAgICAga2xhc3MgPSByZXNwb25zZVsnY2xhc3MnXTsKICAgICAga2xhc3NGdW5jdGlvbiA9IHdpbmRvd1trbGFzc107CiAgICAgIGlmICh0eXBlb2Yga2xhc3NGdW5jdGlvbiA9PT0gdGhpcy5UWVBFX0ZVTkNUSU9OKSB7CiAgICAgICAgcmV0dXJuIGtsYXNzRnVuY3Rpb24obWV0aG9kLCByZXNwb25zZV9kYXRhLCByZXN1bHQpOwogICAgICB9CiAgICB9OwoKICAgIHJldHVybiBNTUpTOwoKICB9KSgpOwogIE1NU0RLSW50ZXJmYWNlID0gKGZ1bmN0aW9uKCkgewogICAgZnVuY3Rpb24gTU1TREtJbnRlcmZhY2UoKSB7CiAgICAgIHRoaXMuc3RhdGUgPSAibG9hZGluZyI7CiAgICAgIHRoaXMuaXNSZWFkeSA9IGZhbHNlOwogICAgICB0aGlzLmFkUHJvcGVydGllcyA9IHt9OwogICAgICB0aGlzLnZpZXdhYmxlID0gZmFsc2U7CiAgICAgIHRoaXMucGxhY2VtZW50VHlwZSA9ICJ1bmtub3duIjsKICAgICAgdGhpcy5hZFNpemUgPSB7fTsKICAgICAgdGhpcy5kZWZhdWx0UG9zaXRpb24gPSB7fTsKICAgICAgdGhpcy51dGlscyA9IE1NSlMudXRpbHM7CiAgICAgIHRoaXMuc3BlZWNoUmVzdWx0cyA9IG51bGw7CiAgICAgIHRoaXMuc3BlZWNoU3RhdHVzID0gInVua25vd24iOwogICAgICB0aGlzLnNwZWVjaEF1ZGlvTGV2ZWwgPSAwOwogICAgICB0aGlzLnNwZWVjaEJhY2tncm91bmRBdWRpb0xldmVsID0gMDsKICAgICAgdGhpcy5hdWRpb1Bvc2l0aW9uID0gMDsKICAgICAgdGhpcy5taWNyb3Bob25lU3RhdGUgPSAicmVhZHkiOwogICAgICB0aGlzLm1pY3JvcGhvbmVBdWRpb0xldmVsID0gMDsKICAgIH0KCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUuc2V0QWRTaXplID0gZnVuY3Rpb24oX3Byb3BlcnRpZXMpIHsKICAgICAgaWYgKHRoaXMuZGVmYXVsdFBvc2l0aW9uICE9IG51bGwpIHsKICAgICAgICB0aGlzLmRlZmF1bHRQb3NpdGlvbiA9IHRoaXMuYWRTaXplOwogICAgICB9CiAgICAgIGlmICh0aGlzLmFkU2l6ZSkgewogICAgICAgIGlmICh0aGlzLmFkU2l6ZVsiaGVpZ2h0Il0gIT09IF9wcm9wZXJ0aWVzWyJoZWlnaHQiXSB8fCB0aGlzLmFkU2l6ZVsid2lkdGgiXSAhPT0gX3Byb3BlcnRpZXNbIndpZHRoIl0pIHsKICAgICAgICAgIHRoaXMuYWRTaXplID0gX3Byb3BlcnRpZXM7CiAgICAgICAgICBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoInNpemVDaGFuZ2UiLCBfcHJvcGVydGllc1sid2lkdGgiXSwgX3Byb3BlcnRpZXNbImhlaWdodCJdKTsKICAgICAgICB9CiAgICAgIH0gZWxzZSB7CiAgICAgICAgdGhpcy5hZFNpemUgPSBfcHJvcGVydGllczsKICAgICAgfQogICAgICByZXR1cm4gdGhpcy51dGlscy5jb25zb2xlTG9nKCJTZXR0aW5nIEFkIFNpemUgIiArIEpTT04uc3RyaW5naWZ5KF9wcm9wZXJ0aWVzKSk7CiAgICB9OwoKICAgIE1NU0RLSW50ZXJmYWNlLnByb3RvdHlwZS5zZXRBZFByb3BlcnRpZXMgPSBmdW5jdGlvbihfYWRQcm9wZXJ0aWVzKSB7CiAgICAgIHRoaXMudXRpbHMuY29uc29sZUxvZygnc2V0QWRQcm9wZXJ0aWVzOiAnICsgSlNPTi5zdHJpbmdpZnkoX2FkUHJvcGVydGllcykpOwogICAgICB0aGlzLmFkUHJvcGVydGllcyA9IF9hZFByb3BlcnRpZXM7CiAgICAgIGlmICh0aGlzLmFkUHJvcGVydGllcyAhPSBudWxsKSB7CiAgICAgICAgaWYgKHRoaXMuYWRQcm9wZXJ0aWVzWyJhZCJdICE9IG51bGwpIHsKICAgICAgICAgIHRoaXMuYWRTaXplID0gdGhpcy5hZFByb3BlcnRpZXNbImFkIl07CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLmFkUHJvcGVydGllc1siZGV2aWNlIl0gIT0gbnVsbCkgewogICAgICAgICAgTU1KUy5kZXZpY2Uuc2V0SW5mbyh0aGlzLmFkUHJvcGVydGllc1siZGV2aWNlIl0pOwogICAgICAgIH0KICAgICAgICBpZiAodGhpcy5hZFByb3BlcnRpZXNbInN1cHBvcnRzIl0gIT0gbnVsbCkgewogICAgICAgICAgcmV0dXJuIHRoaXMuc3VwcG9ydFByb3BlcnRpZXMgPSB0aGlzLmFkUHJvcGVydGllc1sic3VwcG9ydHMiXTsKICAgICAgICB9CiAgICAgIH0KICAgIH07CgogICAgTU1TREtJbnRlcmZhY2UucHJvdG90eXBlLnNldFBsYWNlbWVudFR5cGUgPSBmdW5jdGlvbihwbGFjZW1lbnRUeXBlKSB7CiAgICAgIHRoaXMucGxhY2VtZW50VHlwZSA9IHBsYWNlbWVudFR5cGU7CiAgICB9OwoKICAgIE1NU0RLSW50ZXJmYWNlLnByb3RvdHlwZS5zZXRTdGF0ZSA9IGZ1bmN0aW9uKF9zdGF0ZSkgewogICAgICBpZiAodGhpcy5zdGF0ZSAhPT0gX3N0YXRlKSB7CiAgICAgICAgdGhpcy51dGlscy5jb25zb2xlTG9nKCdNUkFJRCBzdGF0ZSBjaGFuZ2UgZnJvbSAiJyArIHRoaXMuc3RhdGUgKyAnIiB0byAiJyArIF9zdGF0ZSArICciJyk7CiAgICAgICAgdGhpcy5zdGF0ZSA9IF9zdGF0ZTsKICAgICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJzdGF0ZUNoYW5nZSIsIF9zdGF0ZSk7CiAgICAgIH0KICAgIH07CgogICAgTU1TREtJbnRlcmZhY2UucHJvdG90eXBlLnNldFZpZXdhYmxlID0gZnVuY3Rpb24oX3Zpc2libGUpIHsKICAgICAgaWYgKHRoaXMudmlld2FibGUgIT09IF92aXNpYmxlKSB7CiAgICAgICAgdGhpcy51dGlscy5jb25zb2xlTG9nKCdNUkFJRCB2aWV3YWJsZSBjaGFuZ2U6IHZpc2libGUgPSAnICsgX3Zpc2libGUpOwogICAgICAgIHRoaXMudmlld2FibGUgPSBfdmlzaWJsZTsKICAgICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJ2aWV3YWJsZUNoYW5nZSIsIF92aXNpYmxlKTsKICAgICAgfQogICAgfTsKCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUucmVhZHkgPSBmdW5jdGlvbigpIHsKICAgICAgaWYgKHRoaXMuc3RhdGUgIT09ICJsb2FkaW5nIiAmJiB0aGlzLmlzUmVhZHkgPT09IGZhbHNlKSB7CiAgICAgICAgdGhpcy51dGlscy5jb25zb2xlTG9nKCdNUkFJRCByZWFkeS4nKTsKICAgICAgICB0aGlzLnV0aWxzLnBvc3RFdmVudCgic2RrcmVhZHkiKTsKICAgICAgICB0aGlzLmlzUmVhZHkgPSB0cnVlOwogICAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoInJlYWR5Iik7CiAgICAgIH0KICAgIH07CgogICAgTU1TREtJbnRlcmZhY2UucHJvdG90eXBlLmVycm9yID0gZnVuY3Rpb24obWVzc2FnZSwgYWN0aW9uKSB7CiAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoImVycm9yIiwgbWVzc2FnZSwgYWN0aW9uKTsKICAgIH07CgogICAgTU1TREtJbnRlcmZhY2UucHJvdG90eXBlLnZvaWNlU3RhdGVDaGFuZ2UgPSBmdW5jdGlvbihfc3RhdHVzKSB7CiAgICAgIHRoaXMuc3BlZWNoU3RhdHVzID0gX3N0YXR1czsKICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygidm9pY2VTdGF0ZUNoYW5nZSIsIF9zdGF0dXMpOwogICAgfTsKCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUuYXVkaW9MZXZlbENoYW5nZSA9IGZ1bmN0aW9uKF9hdWRpb0xldmVsKSB7CiAgICAgIHRoaXMuc3BlZWNoQXVkaW9MZXZlbCA9IF9hdWRpb0xldmVsOwogICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJhdWRpb0xldmVsQ2hhbmdlIiwgX2F1ZGlvTGV2ZWwpOwogICAgfTsKCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUucmVjb2duaXRpb25SZXN1bHQgPSBmdW5jdGlvbihfcmVzdWx0cykgewogICAgICB0aGlzLnNwZWVjaFJlc3VsdHMgPSBfcmVzdWx0czsKICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygicmVjb2duaXRpb25SZXN1bHQiLCBfcmVzdWx0cyk7CiAgICB9OwoKICAgIE1NU0RLSW50ZXJmYWNlLnByb3RvdHlwZS52b2ljZUVycm9yID0gZnVuY3Rpb24oX2Vycm9yKSB7CiAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoInZvaWNlRXJyb3IiLCBfZXJyb3IpOwogICAgfTsKCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUuYmFja2dyb3VuZEF1ZGlvTGV2ZWwgPSBmdW5jdGlvbihfYmFja2dyb3VuZEF1ZGlvTGV2ZWwpIHsKICAgICAgdGhpcy5zcGVlY2hCYWNrZ3JvdW5kQXVkaW9MZXZlbCA9IF9iYWNrZ3JvdW5kQXVkaW9MZXZlbDsKICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygiYmFja2dyb3VuZEF1ZGlvTGV2ZWwiLCBfYmFja2dyb3VuZEF1ZGlvTGV2ZWwpOwogICAgfTsKCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUuYXVkaW9DYWNoZWQgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygiYXVkaW9DYWNoZWQiKTsKICAgIH07CgogICAgTU1TREtJbnRlcmZhY2UucHJvdG90eXBlLmF1ZGlvU3RhcnRlZCA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJhdWRpb1N0YXJ0ZWQiKTsKICAgIH07CgogICAgTU1TREtJbnRlcmZhY2UucHJvdG90eXBlLmF1ZGlvUG9zaXRpb25DaGFuZ2UgPSBmdW5jdGlvbihfcG9zaXRpb24pIHsKICAgICAgdGhpcy5hdWRpb1Bvc2l0aW9uID0gX3Bvc2l0aW9uOwogICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJhdWRpb1Bvc2l0aW9uQ2hhbmdlIiwgX3Bvc2l0aW9uKTsKICAgIH07CgogICAgTU1TREtJbnRlcmZhY2UucHJvdG90eXBlLmF1ZGlvQ29tcGxldGVkID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoImF1ZGlvQ29tcGxldGVkIik7CiAgICB9OwoKICAgIE1NU0RLSW50ZXJmYWNlLnByb3RvdHlwZS5jdXN0b21Wb2ljZVdvcmRzQWRkZWQgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygiY3VzdG9tVm9pY2VXb3Jkc0FkZGVkIik7CiAgICB9OwoKICAgIE1NU0RLSW50ZXJmYWNlLnByb3RvdHlwZS5jdXN0b21Wb2ljZVdvcmRzRGVsZXRlZCA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJjdXN0b21Wb2ljZVdvcmRzRGVsZXRlZCIpOwogICAgfTsKCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUubWljcm9waG9uZVN0YXRlQ2hhbmdlID0gZnVuY3Rpb24oX21wU3RhdGUpIHsKICAgICAgdGhpcy5taWNyb3Bob25lU3RhdGUgPSBfbXBTdGF0ZTsKICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygibWljcm9waG9uZVN0YXRlQ2hhbmdlIiwgX21wU3RhdGUpOwogICAgfTsKCiAgICBNTVNES0ludGVyZmFjZS5wcm90b3R5cGUubWljcm9waG9uZUF1ZGlvTGV2ZWxDaGFuZ2UgPSBmdW5jdGlvbihfbXBhdWRpb0xldmVsKSB7CiAgICAgIHRoaXMubWljcm9waG9uZUF1ZGlvTGV2ZWwgPSBfbXBhdWRpb0xldmVsOwogICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJtaWNyb3Bob25lQXVkaW9MZXZlbENoYW5nZSIsIF9tcGF1ZGlvTGV2ZWwpOwogICAgfTsKCiAgICByZXR1cm4gTU1TREtJbnRlcmZhY2U7CgogIH0pKCk7CiAgTU1MaXN0ZW5lck1hbmFnZXIgPSAoZnVuY3Rpb24oKSB7CiAgICBmdW5jdGlvbiBNTUxpc3RlbmVyTWFuYWdlcigpIHsKICAgICAgdGhpcy5saXN0ZW5lcnMgPSB7fTsKICAgICAgdGhpcy51dGlscyA9IE1NSlMudXRpbHM7CiAgICB9CgogICAgTU1MaXN0ZW5lck1hbmFnZXIucHJvdG90eXBlLnJlbW92ZUV2ZW50TGlzdGVuZXIgPSBmdW5jdGlvbihldmVudCwgbGlzdGVuZXIpIHsKICAgICAgdmFyIGluZGV4OwoKICAgICAgaWYgKHRoaXMubGlzdGVuZXJzW2V2ZW50XSAhPSBudWxsKSB7CiAgICAgICAgaWYgKGxpc3RlbmVyICE9IG51bGwpIHsKICAgICAgICAgIGluZGV4ID0gdGhpcy5saXN0ZW5lcnNbZXZlbnRdLmluZGV4T2YobGlzdGVuZXIpOwogICAgICAgICAgaWYgKGluZGV4IDwgMCkgewogICAgICAgICAgICB0aGlzLnV0aWxzLmNvbnNvbGVMb2coIkxpc3RuZXIgbm90IGZvdW5kISIpOwogICAgICAgICAgICByZXR1cm4gZmFsc2U7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICB0aGlzLnV0aWxzLmNvbnNvbGVMb2coIiciICsgZXZlbnQgKyAiJyBmb3VuZCBsaXN0ZW5lcjogIiArIGxpc3RlbmVyKTsKICAgICAgICAgIH0KICAgICAgICAgIHRoaXMubGlzdGVuZXJzW2V2ZW50XS5zcGxpY2UoaW5kZXgsIDEpOwogICAgICAgICAgcmV0dXJuIHRoaXMudXRpbHMuY29uc29sZUxvZygiJyIgKyBldmVudCArICInIGxpc3RlbmVyczogIiArIHRoaXMubGlzdGVuZXJzW2V2ZW50XSk7CiAgICAgICAgfSBlbHNlIHsKICAgICAgICAgIHJldHVybiBkZWxldGUgdGhpcy5saXN0ZW5lcnNbZXZlbnRdOwogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICBNTUxpc3RlbmVyTWFuYWdlci5wcm90b3R5cGUuYWRkRXZlbnRMaXN0ZW5lciA9IGZ1bmN0aW9uKGV2ZW50LCBsaXN0ZW5lcikgewogICAgICBpZiAodGhpcy5saXN0ZW5lcnNbZXZlbnRdID09IG51bGwpIHsKICAgICAgICB0aGlzLmxpc3RlbmVyc1tldmVudF0gPSBbXTsKICAgICAgfQogICAgICB0aGlzLnV0aWxzLmNvbnNvbGVMb2coIiciICsgZXZlbnQgKyAiJyBhZGRlZCBsaXN0ZW5lcjogIiArIGxpc3RlbmVyKTsKICAgICAgdGhpcy5saXN0ZW5lcnNbZXZlbnRdLnB1c2gobGlzdGVuZXIpOwogICAgICByZXR1cm4gdGhpcy51dGlscy5jb25zb2xlTG9nKCInIiArIGV2ZW50ICsgIicgbGlzdGVuZXJzOiAiICsgdGhpcy5saXN0ZW5lcnNbZXZlbnRdKTsKICAgIH07CgogICAgTU1MaXN0ZW5lck1hbmFnZXIucHJvdG90eXBlLmZpcmVFdmVudENhbGxiYWNrcyA9IGZ1bmN0aW9uKGV2ZW50TmFtZSwgcGFyYW1ldGVyLCBhY3Rpb24pIHsKICAgICAgdmFyIGNhbGxiYWNrLCBfaSwgX2xlbiwgX3JlZjsKCiAgICAgIHRoaXMudXRpbHMuY29uc29sZUxvZygiZXZlbnQgY2FsbGJhY2s6ICIgKyBldmVudE5hbWUpOwogICAgICBpZiAodGhpcy5saXN0ZW5lcnNbZXZlbnROYW1lXSAhPSBudWxsKSB7CiAgICAgICAgX3JlZiA9IHRoaXMubGlzdGVuZXJzW2V2ZW50TmFtZV07CiAgICAgICAgZm9yIChfaSA9IDAsIF9sZW4gPSBfcmVmLmxlbmd0aDsgX2kgPCBfbGVuOyBfaSsrKSB7CiAgICAgICAgICBjYWxsYmFjayA9IF9yZWZbX2ldOwogICAgICAgICAgaWYgKHBhcmFtZXRlciAhPSBudWxsKSB7CiAgICAgICAgICAgIGlmIChhY3Rpb24gIT0gbnVsbCkgewogICAgICAgICAgICAgIGNhbGxiYWNrKHBhcmFtZXRlciwgYWN0aW9uKTsKICAgICAgICAgICAgfSBlbHNlIHsKICAgICAgICAgICAgICBjYWxsYmFjayhwYXJhbWV0ZXIpOwogICAgICAgICAgICB9CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBjYWxsYmFjaygpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgfTsKCiAgICByZXR1cm4gTU1MaXN0ZW5lck1hbmFnZXI7CgogIH0pKCk7CiAgTU1Db21tYW5kID0gKGZ1bmN0aW9uKCkgewogICAgTU1Db21tYW5kLnVybCA9IG51bGw7CgogICAgTU1Db21tYW5kLnBsYXRmb3JtID0gbnVsbDsKCiAgICBNTUNvbW1hbmQuY29tbWFuZCA9IG51bGw7CgogICAgTU1Db21tYW5kLmNhbGxiYWNrID0gbnVsbDsKCiAgICBmdW5jdGlvbiBNTUNvbW1hbmQoY29tbWFuZCwgcGFyYW1zKSB7CiAgICAgIHZhciBmdW5jLCBmdW5jdGlvbk5hbWUsIG5hbWUsIHF1ZXJ5X2FyZ3MsIHRpbWVzdGFtcCwgdXJsOwoKICAgICAgdGhpcy51dGlscyA9IE1NSlMudXRpbHM7CiAgICAgIHRoaXMucGxhdGZvcm0gPSB0aGlzLnV0aWxzLmdldFBsYXRmb3JtKCk7CiAgICAgIHRoaXMuY29tbWFuZCA9IGNvbW1hbmQ7CiAgICAgIHVybCA9ICJtbXNkazovLyIgKyBjb21tYW5kICsgIi8iOwogICAgICBpZiAocGFyYW1zICE9IG51bGwpIHsKICAgICAgICBxdWVyeV9hcmdzID0gW107CiAgICAgICAgdGltZXN0YW1wID0gbmV3IERhdGUoKS5nZXRUaW1lKCk7CiAgICAgICAgZnVuYyA9IHBhcmFtc1siY2FsbGJhY2siXTsKICAgICAgICBmdW5jdGlvbk5hbWUgPSB0aGlzLmNvbW1hbmQucmVwbGFjZSgiLiIsICJfIikgKyAiXyIgKyB0aW1lc3RhbXA7CiAgICAgICAgTU1KUy51dGlscy5jb25zb2xlTG9nKCJjb21tYW5kOiAiICsgY29tbWFuZCArICJDYWxsYmFjayBmdW5jdGlvbjogIiArIGZ1bmMpOwogICAgICAgIE1NSlMudXRpbHMuY29uc29sZUxvZygiY29tbWFuZDogIiArIGNvbW1hbmQgKyAiIHBhcmFtcyAiICsgSlNPTi5zdHJpbmdpZnkocGFyYW1zKSk7CiAgICAgICAgTU1KUy51dGlscy5jb25zb2xlTG9nKCJDYWxsYmFjayBmdW5jdGlvbjogIiArICh0eXBlb2YgZnVuYykpOwogICAgICAgIGlmICh0eXBlb2YgZnVuYyA9PT0gTU1KUy5UWVBFX1NUUklORykgewogICAgICAgICAgd2luZG93WyJNTUpTIl1bImNhbGxiYWNrcyJdW2Z1bmN0aW9uTmFtZV0gPSBmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgICAgICB2YXIgYUZ1bmMsIGNvbnRleHQsIGksIG5hbWVzcGFjZXM7CgogICAgICAgICAgICBNTUpTLnV0aWxzLmNvbnNvbGVMb2coImV4ZWN1dGluZyBzdHJpbmcgZnVuY3Rpb24gY2FsbGJhY2s6ICIgKyBmdW5jdGlvbk5hbWUpOwogICAgICAgICAgICBpZiAocmVzcG9uc2UgIT0gbnVsbCkgewogICAgICAgICAgICAgIHJlc3BvbnNlWydkYXRhJ10gPSByZXNwb25zZVsncmVzcG9uc2UnXTsKICAgICAgICAgICAgfQogICAgICAgICAgICBuYW1lc3BhY2VzID0gZnVuYy5zcGxpdCgiLiIpOwogICAgICAgICAgICBhRnVuYyA9IG5hbWVzcGFjZXMucG9wKCk7CiAgICAgICAgICAgIGkgPSAwOwogICAgICAgICAgICBjb250ZXh0ID0gd2luZG93OwogICAgICAgICAgICB3aGlsZSAoaSA8IG5hbWVzcGFjZXMubGVuZ3RoKSB7CiAgICAgICAgICAgICAgTU1KUy51dGlscy5jb25zb2xlTG9nKCJuYW1lc3BhY2U6ICIgKyBuYW1lc3BhY2VzW2ldKTsKICAgICAgICAgICAgICBjb250ZXh0ID0gY29udGV4dFtuYW1lc3BhY2VzW2ldXTsKICAgICAgICAgICAgICBpKys7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgTU1KUy51dGlscy5jb25zb2xlTG9nKCJhRnVuYzogIiArIGFGdW5jKTsKICAgICAgICAgICAgTU1KUy51dGlscy5jb25zb2xlTG9nKCJjb250ZXh0OiAiICsgY29udGV4dCk7CiAgICAgICAgICAgIGNvbnRleHRbYUZ1bmNdKHJlc3BvbnNlKTsKICAgICAgICAgICAgcmV0dXJuIE1NSlMuc2V0RXhlY3V0aW5nQ29tbWFuZChmYWxzZSk7CiAgICAgICAgICB9OwogICAgICAgIH0gZWxzZSBpZiAodHlwZW9mIGZ1bmMgPT09IE1NSlMuVFlQRV9GVU5DVElPTikgewogICAgICAgICAgd2luZG93WyJNTUpTIl1bImNhbGxiYWNrcyJdW2Z1bmN0aW9uTmFtZV0gPSBmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgICAgICBpZiAocmVzcG9uc2UgIT0gbnVsbCkgewogICAgICAgICAgICAgIHJlc3BvbnNlWydkYXRhJ10gPSByZXNwb25zZVsncmVzcG9uc2UnXTsKICAgICAgICAgICAgICByZXNwb25zZVsncmVzdWx0J10gPSBwYXJzZUludChyZXNwb25zZVsncmVzdWx0J10pOwogICAgICAgICAgICB9CiAgICAgICAgICAgIGZ1bmMocmVzcG9uc2UpOwogICAgICAgICAgICByZXR1cm4gTU1KUy5zZXRFeGVjdXRpbmdDb21tYW5kKGZhbHNlKTsKICAgICAgICAgIH07CiAgICAgICAgfSBlbHNlIGlmICh0eXBlb2YgZnVuYyA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICAgICAgd2luZG93WyJNTUpTIl1bImNhbGxiYWNrcyJdW2Z1bmN0aW9uTmFtZV0gPSBmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgICAgICBNTUpTLnV0aWxzLmNvbnNvbGVMb2coImV4ZWN1dGluZyB1bmRlZmluZWQgY2FsbGJhY2s6ICIgKyBmdW5jdGlvbk5hbWUpOwogICAgICAgICAgICBNTUpTLnV0aWxzLmNvbnNvbGVMb2coIm5vIGNhbGxiYWNrIHdhcyBzcGVjaWZpZWQiKTsKICAgICAgICAgICAgcmV0dXJuIE1NSlMuc2V0RXhlY3V0aW5nQ29tbWFuZChmYWxzZSk7CiAgICAgICAgICB9OwogICAgICAgIH0KICAgICAgICBwYXJhbXNbImNhbGxiYWNrIl0gPSAiTU1KUy5jYWxsYmFja3MuIiArIGZ1bmN0aW9uTmFtZTsKICAgICAgICB0aGlzLmNhbGxiYWNrID0gcGFyYW1zWyJjYWxsYmFjayJdOwogICAgICAgIGZvciAobmFtZSBpbiBwYXJhbXMpIHsKICAgICAgICAgIGlmICh0eXBlb2YgbmFtZSAhPT0gTU1KUy5UWVBFX1NUUklORykgewogICAgICAgICAgICBjb250aW51ZTsKICAgICAgICAgIH0KICAgICAgICAgIGlmIChwYXJhbXNbbmFtZV0gPT09IHZvaWQgMCB8fCBwYXJhbXNbbmFtZV0gPT09IG51bGwpIHsKICAgICAgICAgICAgY29udGludWU7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBxdWVyeV9hcmdzLnB1c2goZW5jb2RlVVJJQ29tcG9uZW50KG5hbWUpICsgIj0iICsgZW5jb2RlVVJJQ29tcG9uZW50KHBhcmFtc1tuYW1lXSkpOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgICBpZiAocXVlcnlfYXJncy5sZW5ndGggPiAwKSB7CiAgICAgICAgICB1cmwgKz0gIj8iICsgcXVlcnlfYXJncy5qb2luKCImIik7CiAgICAgICAgfQogICAgICB9CiAgICAgIE1NSlMudXRpbHMuY29uc29sZUxvZyh1cmwpOwogICAgICB0aGlzLnVybCA9IHVybDsKICAgICAgdGhpczsKICAgIH0KCiAgICBNTUNvbW1hbmQucHJvdG90eXBlLnBlcmZvcm0gPSBmdW5jdGlvbigpIHsKICAgICAgdmFyIGlmcmFtZTsKCiAgICAgIHRoaXMudXRpbHMuY29uc29sZUxvZygicGVyZm9ybSBwbGF0Zm9ybTogICIgKyB0aGlzLnBsYXRmb3JtKTsKICAgICAgdGhpcy51dGlscy5jb25zb2xlTG9nKCJjdXJyZW50IHdpbmRvdy5sb2NhdGlvbjogICIgKyB3aW5kb3cubG9jYXRpb24pOwogICAgICBNTUpTLmV4ZWN1dGluZ0NvbW1hbmQgPSB0cnVlOwogICAgICB0aGlzLnV0aWxzLmNvbnNvbGVMb2coIndpbmRvdy5sb2NhdGlvbjogICIgKyB0aGlzLnVybCk7CiAgICAgIHRoaXMudXRpbHMuY29uc29sZUxvZygiU2V0dGluZyBleGVjdXRpbmdDb21tYW5kID0gdHJ1ZTogICIpOwogICAgICBpZnJhbWUgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCJJRlJBTUUiKTsKICAgICAgaWZyYW1lLnNldEF0dHJpYnV0ZSgic3JjIiwgdGhpcy51cmwpOwogICAgICBkb2N1bWVudC5kb2N1bWVudEVsZW1lbnQuYXBwZW5kQ2hpbGQoaWZyYW1lKTsKICAgICAgaWZyYW1lLnBhcmVudE5vZGUucmVtb3ZlQ2hpbGQoaWZyYW1lKTsKICAgICAgcmV0dXJuIGlmcmFtZSA9IG51bGw7CiAgICB9OwoKICAgIHJldHVybiBNTUNvbW1hbmQ7CgogIH0pKCk7CiAgTU1CcmlkZ2VPYmplY3QgPSAoZnVuY3Rpb24oKSB7CiAgICBNTUJyaWRnZU9iamVjdC5jbGFzc05hbWUgPSBudWxsOwoKICAgIGZ1bmN0aW9uIE1NQnJpZGdlT2JqZWN0KCkgewogICAgICB2YXIgbTsKCiAgICAgIHRoaXMudXRpbHMgPSBNTUpTLnV0aWxzOwogICAgICBtID0gdGhpcy5jb25zdHJ1Y3Rvci50b1N0cmluZygpLm1hdGNoKC9eXHMqZnVuY3Rpb25ccysoW15cc1woXSspLyk7CiAgICAgIGlmIChtKSB7CiAgICAgICAgdGhpcy5jbGFzc05hbWUgPSBtWzFdOwogICAgICB9CiAgICB9CgogICAgTU1CcmlkZ2VPYmplY3QucHJvdG90eXBlLmVucXVldWUgPSBmdW5jdGlvbihtZXRob2QsIHBhcmFtcykgewogICAgICBNTUpTLmVucXVldWVDb21tYW5kKG5ldyBNTUNvbW1hbmQodGhpcy5jbGFzc05hbWUgKyAiLiIgKyBtZXRob2QsIHBhcmFtcykpOwogICAgICByZXR1cm4gdHJ1ZTsKICAgIH07CgogICAgcmV0dXJuIE1NQnJpZGdlT2JqZWN0OwoKICB9KSgpOwogIE1NRGV2aWNlID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NRGV2aWNlLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NRGV2aWNlKCkgewogICAgICBfcmVmID0gTU1EZXZpY2UuX19zdXBlcl9fLmNvbnN0cnVjdG9yLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIHJldHVybiBfcmVmOwogICAgfQoKICAgIE1NRGV2aWNlLmxvYWRTdGF0ZSA9ICJzdGFuZGJ5IjsKCiAgICBNTURldmljZS5sb2FkVGltZW91dCA9IDA7CgogICAgTU1EZXZpY2UuY29ubmVjdGlvbiA9IG51bGw7CgogICAgTU1EZXZpY2UucHJvdG90eXBlLnNldE5ldHdvcmtDb25uZWN0aW9uID0gZnVuY3Rpb24obmV0d29yaykgewogICAgICByZXR1cm4gdGhpcy5jb25uZWN0aW9uID0gbmV0d29yazsKICAgIH07CgogICAgTU1EZXZpY2UucHJvdG90eXBlLnNldEluZm8gPSBmdW5jdGlvbihpbmZvKSB7CiAgICAgIHZhciBldnQsIGtleSwgdmFsdWU7CgogICAgICBmb3IgKGtleSBpbiBpbmZvKSB7CiAgICAgICAgdmFsdWUgPSBpbmZvW2tleV07CiAgICAgICAgdGhpc1trZXldID0gdmFsdWU7CiAgICAgIH0KICAgICAgTU1EZXZpY2UubG9hZFN0YXRlID0gImxvYWRlZCI7CiAgICAgIGlmICghdGhpcy51dGlscy5pc1dpbmRvd3MoKSkgewogICAgICAgIGV2dCA9ICJkZXZpY2VMb2FkZWQiOwogICAgICAgIHRoaXMudXRpbHMucG9zdEV2ZW50KGV2dCk7CiAgICAgICAgZXZ0ID0gImRldmljZWxvYWRlZCI7CiAgICAgICAgdGhpcy51dGlscy5wb3N0RXZlbnQoZXZ0KTsKICAgICAgfQogICAgICByZXR1cm4gdHJ1ZTsKICAgIH07CgogICAgTU1EZXZpY2UucHJvdG90eXBlLmdldEluZm8gPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICBNTURldmljZS5sb2FkU3RhdGUgPSAibG9hZGluZyI7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImdldEluZm8iLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTURldmljZS5wcm90b3R5cGUuc2V0TU1ESUQgPSBmdW5jdGlvbihtbWRpZCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgic2V0TU1ESUQiLCB7CiAgICAgICAgbW1kaWQ6IG1tZGlkLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1EZXZpY2UucHJvdG90eXBlLmdldEF2YWlsYWJsZVNjaGVtZXMgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRBdmFpbGFibGVTY2hlbWVzIiwgewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1EZXZpY2UucHJvdG90eXBlLmlzU2NoZW1lQXZhaWxhYmxlID0gZnVuY3Rpb24oc2NoZW1lLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJpc1NjaGVtZUF2YWlsYWJsZSIsIHsKICAgICAgICBzY2hlbWU6IHNjaGVtZSwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRGV2aWNlLnByb3RvdHlwZS5nZXRBdmFpbGFibGVTY2hlbWVzID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiZ2V0QXZhaWxhYmxlU2NoZW1lcyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRGV2aWNlLnByb3RvdHlwZS5nZXRPcmllbnRhdGlvbiA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImdldE9yaWVudGF0aW9uIiwgewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1EZXZpY2UucHJvdG90eXBlLmdldExvY2F0aW9uID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiZ2V0TG9jYXRpb24iLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTURldmljZS5wcm90b3R5cGUuc2hvd01hcCA9IGZ1bmN0aW9uKGxvY2F0aW9uLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJzaG93TWFwIiwgewogICAgICAgIGxvY2F0aW9uOiBsb2NhdGlvbiwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRGV2aWNlLnByb3RvdHlwZS5jYWxsID0gZnVuY3Rpb24obnVtYmVyLCBkaWFsLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJjYWxsIiwgewogICAgICAgIG51bWJlcjogbnVtYmVyLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjaywKICAgICAgICBkaWFsOiBkaWFsCiAgICAgIH0pOwogICAgfTsKCiAgICBNTURldmljZS5wcm90b3R5cGUub3BlblVybCA9IGZ1bmN0aW9uKHVybCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgib3BlblVybCIsIHsKICAgICAgICB1cmw6IHVybCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRGV2aWNlLnByb3RvdHlwZS5vcGVuQXBwU3RvcmUgPSBmdW5jdGlvbihhcHBJZCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgib3BlbkFwcFN0b3JlIiwgewogICAgICAgIGFwcElkOiBhcHBJZCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRGV2aWNlLnByb3RvdHlwZS5jb21wb3NlU01TID0gZnVuY3Rpb24obnVtYmVyLCBtZXNzYWdlLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5jb21wb3NlU21zKG51bWJlciwgbWVzc2FnZSwgY2FsbGJhY2spOwogICAgfTsKCiAgICBNTURldmljZS5wcm90b3R5cGUuY29tcG9zZVNtcyA9IGZ1bmN0aW9uKG51bWJlciwgbWVzc2FnZSwgY2FsbGJhY2spIHsKICAgICAgaWYgKHRoaXMudXRpbHMuaXNJT1MoKSkgewogICAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImNvbXBvc2VTbXMiLCB7CiAgICAgICAgICBudW1iZXI6IG51bWJlciwKICAgICAgICAgIG1lc3NhZ2U6IG1lc3NhZ2UsCiAgICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgICB9KTsKICAgICAgfSBlbHNlIHsKICAgICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJjb21wb3NlU21zIiwgewogICAgICAgICAgbnVtYmVyOiBudW1iZXIsCiAgICAgICAgICBtZXNzYWdlOiBtZXNzYWdlLAogICAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgICAgfSk7CiAgICAgIH0KICAgIH07CgogICAgTU1EZXZpY2UucHJvdG90eXBlLmNvbXBvc2VFbWFpbCA9IGZ1bmN0aW9uKHJlY2lwaWVudCwgc3ViamVjdCwgbWVzc2FnZSwgY2FsbGJhY2spIHsKICAgICAgaWYgKHRoaXMudXRpbHMuaXNJT1MoKSkgewogICAgICAgIHJldHVybiB0aGlzLm9wZW5VcmwoIm1haWx0bzo/dG89IiArIGVuY29kZVVSSUNvbXBvbmVudChyZWNpcGllbnQpICsgIiZzdWJqZWN0PSIgKyBlbmNvZGVVUklDb21wb25lbnQoc3ViamVjdCkgKyAiJmJvZHk9IiArIGVuY29kZVVSSUNvbXBvbmVudChtZXNzYWdlKSwgY2FsbGJhY2spOwogICAgICB9IGVsc2UgewogICAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImNvbXBvc2VFbWFpbCIsIHsKICAgICAgICAgIHJlY2lwaWVudDogcmVjaXBpZW50LAogICAgICAgICAgc3ViamVjdDogc3ViamVjdCwKICAgICAgICAgIG1lc3NhZ2U6IG1lc3NhZ2UsCiAgICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgICB9KTsKICAgICAgfQogICAgfTsKCiAgICBNTURldmljZS5wcm90b3R5cGUuZ2V0Q29tcGFzc0hlYWRpbmcgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRDb21wYXNzSGVhZGluZyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRGV2aWNlLnByb3RvdHlwZS5nZXRCYXJvbWV0ZXIgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRCYXJvbWV0ZXIiLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTURldmljZS5wcm90b3R5cGUuZW5hYmxlSGFyZHdhcmVBY2NlbGVyYXRpb24gPSBmdW5jdGlvbihlbmFibGVkLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJlbmFibGVIYXJkd2FyZUFjY2VsZXJhdGlvbiIsIHsKICAgICAgICBlbmFibGVkOiBlbmFibGVkLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgcmV0dXJuIE1NRGV2aWNlOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgTU1NZWRpYSA9IChmdW5jdGlvbihfc3VwZXIpIHsKICAgIF9fZXh0ZW5kcyhNTU1lZGlhLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NTWVkaWEoKSB7CiAgICAgIF9yZWYxID0gTU1NZWRpYS5fX3N1cGVyX18uY29uc3RydWN0b3IuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIF9yZWYxOwogICAgfQoKICAgIE1NTWVkaWEucHJvdG90eXBlLm9wZW5Gcm9udENhbWVyYSA9IGZ1bmN0aW9uKGNvbnN0cmFpbldpZHRoLCBjb25zdHJhaW5IZWlnaHQsIGNvbnRlbnRNb2RlLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRQaWN0dXJlIiwgewogICAgICAgIHNvdXJjZVR5cGU6ICdDYW1lcmEnLAogICAgICAgIGNvbnN0cmFpbldpZHRoOiBjb25zdHJhaW5XaWR0aCwKICAgICAgICBjb25zdHJhaW5IZWlnaHQ6IGNvbnN0cmFpbkhlaWdodCwKICAgICAgICBjb250ZW50TW9kZTogY29udGVudE1vZGUsCiAgICAgICAgZnJvbnQ6IHRydWUsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTU1lZGlhLnByb3RvdHlwZS5vcGVuUmVhckNhbWVyYSA9IGZ1bmN0aW9uKGNvbnN0cmFpbldpZHRoLCBjb25zdHJhaW5IZWlnaHQsIGNvbnRlbnRNb2RlLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRQaWN0dXJlIiwgewogICAgICAgIHNvdXJjZVR5cGU6ICdDYW1lcmEnLAogICAgICAgIGNvbnN0cmFpbldpZHRoOiBjb25zdHJhaW5XaWR0aCwKICAgICAgICBjb25zdHJhaW5IZWlnaHQ6IGNvbnN0cmFpbkhlaWdodCwKICAgICAgICBjb250ZW50TW9kZTogY29udGVudE1vZGUsCiAgICAgICAgZnJvbnQ6IGZhbHNlLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1NZWRpYS5wcm90b3R5cGUuZ2V0UGljdHVyZSA9IGZ1bmN0aW9uKHNvdXJjZVR5cGUsIGNvbnN0cmFpbldpZHRoLCBjb25zdHJhaW5IZWlnaHQsIGNvbnRlbnRNb2RlLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRQaWN0dXJlIiwgewogICAgICAgIHNvdXJjZVR5cGU6IHNvdXJjZVR5cGUsCiAgICAgICAgY29uc3RyYWluV2lkdGg6IGNvbnN0cmFpbldpZHRoLAogICAgICAgIGNvbnN0cmFpbkhlaWdodDogY29uc3RyYWluSGVpZ2h0LAogICAgICAgIGNvbnRlbnRNb2RlOiBjb250ZW50TW9kZSwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NTWVkaWEucHJvdG90eXBlLndyaXRlVG9QaG90b0xpYnJhcnkgPSBmdW5jdGlvbihwYXRoLCB0aXRsZSwgZGVzY3JpcHRpb24sIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoIndyaXRlVG9QaG90b0xpYnJhcnkiLCB7CiAgICAgICAgcGF0aDogcGF0aCwKICAgICAgICB0aXRsZTogdGl0bGUsCiAgICAgICAgZGVzY3JpcHRpb246IGRlc2NyaXB0aW9uLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1NZWRpYS5wcm90b3R5cGUuaXNTb3VyY2VUeXBlQXZhaWxhYmxlID0gZnVuY3Rpb24oc291cmNlVHlwZSwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiaXNTb3VyY2VUeXBlQXZhaWxhYmxlIiwgewogICAgICAgIHNvdXJjZVR5cGU6IHNvdXJjZVR5cGUsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTU1lZGlhLnByb3RvdHlwZS5hdmFpbGFibGVTb3VyY2VUeXBlcyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImF2YWlsYWJsZVNvdXJjZVR5cGVzIiwgewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1NZWRpYS5wcm90b3R5cGUucGxheVZpZGVvID0gZnVuY3Rpb24ocGF0aCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgicGxheVZpZGVvIiwgewogICAgICAgIHBhdGg6IHBhdGgsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTU1lZGlhLnByb3RvdHlwZS5wbGF5QXVkaW8gPSBmdW5jdGlvbihwYXRoLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJwbGF5QXVkaW8iLCB7CiAgICAgICAgcGF0aDogcGF0aCwKICAgICAgICAicmVwZWF0IjogZmFsc2UsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTU1lZGlhLnByb3RvdHlwZS5wbGF5QXVkaW8gPSBmdW5jdGlvbihwYXRoLCByZXBlYXQsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInBsYXlBdWRpbyIsIHsKICAgICAgICBwYXRoOiBwYXRoLAogICAgICAgIHJlcGVhdDogcmVwZWF0LAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1NZWRpYS5wcm90b3R5cGUuc3RvcEF1ZGlvID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgic3RvcEF1ZGlvIiwgewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1NZWRpYS5wcm90b3R5cGUucGxheVNvdW5kID0gZnVuY3Rpb24ocGF0aCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgicGxheVNvdW5kIiwgewogICAgICAgIHBhdGg6IHBhdGgsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTU1lZGlhLnByb3RvdHlwZS5nZXREZXZpY2VWb2x1bWUgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXREZXZpY2VWb2x1bWUiLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICByZXR1cm4gTU1NZWRpYTsKCiAgfSkoTU1CcmlkZ2VPYmplY3QpOwogIE1NQ2FsZW5kYXIgPSAoZnVuY3Rpb24oX3N1cGVyKSB7CiAgICBfX2V4dGVuZHMoTU1DYWxlbmRhciwgX3N1cGVyKTsKCiAgICBmdW5jdGlvbiBNTUNhbGVuZGFyKCkgewogICAgICBfcmVmMiA9IE1NQ2FsZW5kYXIuX19zdXBlcl9fLmNvbnN0cnVjdG9yLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIHJldHVybiBfcmVmMjsKICAgIH0KCiAgICBNTUNhbGVuZGFyLnByb3RvdHlwZS5hZGRFdmVudCA9IGZ1bmN0aW9uKHBhcmFtZXRlcnMsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImFkZEV2ZW50IiwgewogICAgICAgICJwYXJhbWV0ZXJzIjogSlNPTi5zdHJpbmdpZnkocGFyYW1ldGVycyksCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICByZXR1cm4gTU1DYWxlbmRhcjsKCiAgfSkoTU1CcmlkZ2VPYmplY3QpOwogIE1NQmFubmVyID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NQmFubmVyLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NQmFubmVyKCkgewogICAgICBfcmVmMyA9IE1NQmFubmVyLl9fc3VwZXJfXy5jb25zdHJ1Y3Rvci5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gX3JlZjM7CiAgICB9CgogICAgTU1CYW5uZXIucHJvdG90eXBlLnJlc2l6ZSA9IGZ1bmN0aW9uKHBhcmFtZXRlcnMsIGNhbGxiYWNrKSB7CiAgICAgIHBhcmFtZXRlcnNbImNhbGxiYWNrIl0gPSBjYWxsYmFjazsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgicmVzaXplIiwgcGFyYW1ldGVycyk7CiAgICB9OwoKICAgIHJldHVybiBNTUJhbm5lcjsKCiAgfSkoTU1CcmlkZ2VPYmplY3QpOwogIE1NTm90aWZpY2F0aW9uID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NTm90aWZpY2F0aW9uLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NTm90aWZpY2F0aW9uKCkgewogICAgICBfcmVmNCA9IE1NTm90aWZpY2F0aW9uLl9fc3VwZXJfXy5jb25zdHJ1Y3Rvci5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gX3JlZjQ7CiAgICB9CgogICAgTU1Ob3RpZmljYXRpb24ucHJvdG90eXBlLmFsZXJ0ID0gZnVuY3Rpb24odGl0bGUsIG1lc3NhZ2UsIGNhbmNlbEJ1dHRvbiwgYnV0dG9ucywgY2FsbGJhY2spIHsKICAgICAgdmFyIHBhcmFtczsKCiAgICAgIHBhcmFtcyA9IHsKICAgICAgICB0aXRsZTogdGl0bGUsCiAgICAgICAgbWVzc2FnZTogbWVzc2FnZSwKICAgICAgICBjYW5jZWxCdXR0b246IGNhbmNlbEJ1dHRvbiwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfTsKICAgICAgaWYgKGJ1dHRvbnMgIT0gbnVsbCkgewogICAgICAgIGlmIChidXR0b25zICE9PSAiIiAmJiBidXR0b25zICE9PSBudWxsKSB7CiAgICAgICAgICBwYXJhbXNbImJ1dHRvbnMiXSA9IGJ1dHRvbnM7CiAgICAgICAgfQogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImFsZXJ0IiwgcGFyYW1zKTsKICAgIH07CgogICAgTU1Ob3RpZmljYXRpb24ucHJvdG90eXBlLnZpYnJhdGUgPSBmdW5jdGlvbihkdXJhdGlvbiwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgidmlicmF0ZSIsIHsKICAgICAgICBkdXJhdGlvbjogZHVyYXRpb24sCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICByZXR1cm4gTU1Ob3RpZmljYXRpb247CgogIH0pKE1NQnJpZGdlT2JqZWN0KTsKICBNTUZpbGVNYW5hZ2VyID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NRmlsZU1hbmFnZXIsIF9zdXBlcik7CgogICAgZnVuY3Rpb24gTU1GaWxlTWFuYWdlcigpIHsKICAgICAgX3JlZjUgPSBNTUZpbGVNYW5hZ2VyLl9fc3VwZXJfXy5jb25zdHJ1Y3Rvci5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gX3JlZjU7CiAgICB9CgogICAgTU1GaWxlTWFuYWdlci5wcm90b3R5cGUuZ2V0RnJlZURpc2tTcGFjZSA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImdldEZyZWVEaXNrU3BhY2UiLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUZpbGVNYW5hZ2VyLnByb3RvdHlwZS5nZXREaXJlY3RvcnlDb250ZW50cyA9IGZ1bmN0aW9uKHBhdGgsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImdldERpcmVjdG9yeUNvbnRlbnRzIiwgewogICAgICAgIHBhdGg6IHBhdGgsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUZpbGVNYW5hZ2VyLnByb3RvdHlwZS5nZXRGaWxlQ29udGVudHMgPSBmdW5jdGlvbihwYXRoLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRGaWxlQ29udGVudHMiLCB7CiAgICAgICAgcGF0aDogcGF0aCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRmlsZU1hbmFnZXIucHJvdG90eXBlLndyaXRlRGF0YSA9IGZ1bmN0aW9uKGRhdGEsIHBhdGgsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoIndyaXRlRGF0YSIsIHsKICAgICAgICBkYXRhOiBkYXRhLAogICAgICAgIHBhdGg6IHBhdGgsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUZpbGVNYW5hZ2VyLnByb3RvdHlwZS5tb3ZlRmlsZSA9IGZ1bmN0aW9uKGZyb21QYXRoLCB0b1BhdGgsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoIm1vdmVGaWxlIiwgewogICAgICAgIGZyb21QYXRoOiBmcm9tUGF0aCwKICAgICAgICB0b1BhdGg6IHRvUGF0aCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NRmlsZU1hbmFnZXIucHJvdG90eXBlLnJlbW92ZUF0UGF0aCA9IGZ1bmN0aW9uKHBhdGgsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInJlbW92ZUF0UGF0aCIsIHsKICAgICAgICBwYXRoOiBwYXRoLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1GaWxlTWFuYWdlci5wcm90b3R5cGUuZG93bmxvYWRGaWxlID0gZnVuY3Rpb24odXJsLCBwYXRoLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJkb3dubG9hZEZpbGUiLCB7CiAgICAgICAgdXJsOiB1cmwsCiAgICAgICAgcGF0aDogcGF0aCwKICAgICAg";
    private static final String MMJS_1_4_PART2 = "ICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIHJldHVybiBNTUZpbGVNYW5hZ2VyOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgTU1JbmxpbmVWaWRlbyA9IChmdW5jdGlvbihfc3VwZXIpIHsKICAgIF9fZXh0ZW5kcyhNTUlubGluZVZpZGVvLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NSW5saW5lVmlkZW8oKSB7CiAgICAgIF9yZWY2ID0gTU1JbmxpbmVWaWRlby5fX3N1cGVyX18uY29uc3RydWN0b3IuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIF9yZWY2OwogICAgfQoKICAgIE1NSW5saW5lVmlkZW8ucHJvdG90eXBlLnVwZGF0ZVZpZGVvU2Vla1RpbWUgPSBmdW5jdGlvbihjdXJyZW50U2Vla1RpbWUpIHsKICAgICAgaWYgKHRoaXMudGltaW5nQ2FsbGJhY2sgIT0gbnVsbCkgewogICAgICAgIHJldHVybiB0aGlzLnRpbWluZ0NhbGxiYWNrKGN1cnJlbnRTZWVrVGltZSk7CiAgICAgIH0KICAgIH07CgogICAgTU1JbmxpbmVWaWRlby5wcm90b3R5cGUuc2V0VGltaW5nQ2FsbGJhY2sgPSBmdW5jdGlvbihfdGltaW5nQ2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMudGltaW5nQ2FsbGJhY2sgPSBfdGltaW5nQ2FsbGJhY2s7CiAgICB9OwoKICAgIE1NSW5saW5lVmlkZW8ucHJvdG90eXBlLnBsYXlWaWRlbyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInBsYXlWaWRlbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NSW5saW5lVmlkZW8ucHJvdG90eXBlLnN0b3BWaWRlbyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInN0b3BWaWRlbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NSW5saW5lVmlkZW8ucHJvdG90eXBlLnBhdXNlVmlkZW8gPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJwYXVzZVZpZGVvIiwgewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1JbmxpbmVWaWRlby5wcm90b3R5cGUucmVzdW1lVmlkZW8gPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJyZXN1bWVWaWRlbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NSW5saW5lVmlkZW8ucHJvdG90eXBlLnJlbW92ZVZpZGVvID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgicmVtb3ZlVmlkZW8iLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUlubGluZVZpZGVvLnByb3RvdHlwZS5zZXRTdHJlYW1WaWRlb1NvdXJjZSA9IGZ1bmN0aW9uKHN0cmVhbVZpZGVvVVJJLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJzZXRTdHJlYW1WaWRlb1NvdXJjZSIsIHsKICAgICAgICBzdHJlYW1WaWRlb1VSSTogc3RyZWFtVmlkZW9VUkksCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUlubGluZVZpZGVvLnByb3RvdHlwZS5hZGp1c3RWaWRlbyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmFkanVzdFZpZGVvV2l0aElkKCdpbmxpbmVWaWRlbycsIGNhbGxiYWNrKTsKICAgIH07CgogICAgTU1JbmxpbmVWaWRlby5wcm90b3R5cGUuYWRqdXN0VmlkZW9XaXRoSWQgPSBmdW5jdGlvbihkaXZJZCwgY2FsbGJhY2spIHsKICAgICAgdmFyIGZyYW1lLCB2aWRlb0VsOwoKICAgICAgdmlkZW9FbCA9IGRvY3VtZW50LmdldEVsZW1lbnRCeUlkKGRpdklkKTsKICAgICAgaWYgKHZpZGVvRWwgIT0gbnVsbCkgewogICAgICAgIGZyYW1lID0gdGhpcy5jYWxjdWxhdGVEaXZQb3NpdGlvbihkaXZJZCk7CiAgICAgICAgZnJhbWVbImNhbGxiYWNrIl0gPSBjYWxsYmFjazsKICAgICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJhZGp1c3RWaWRlbyIsIGZyYW1lKTsKICAgICAgfSBlbHNlIHsKICAgICAgICByZXR1cm4gY2FsbGJhY2soewogICAgICAgICAgInJlc3VsdCI6IDAsCiAgICAgICAgICAicmVzcG9uc2UiOiAiRGl2IElkIG5vdCBmb3VuZCIsCiAgICAgICAgICAiY2xhc3MiOiAiTU1JbmxpbmVWaWRlbyIsCiAgICAgICAgICAiY2FsbCI6ICJpbnNlcnRWaWRlbyIKICAgICAgICB9KTsKICAgICAgfQogICAgfTsKCiAgICBNTUlubGluZVZpZGVvLnByb3RvdHlwZS5pbnNlcnRWaWRlb1dpdGhJZCA9IGZ1bmN0aW9uKGRpdklkLCB0aW1pbmdDYWxsYmFjaywgY2FsbGJhY2spIHsKICAgICAgdmFyIGF1dG9QbGF5LCBib2R5SGVpZ2h0LCBib2R5V2lkdGgsIGNhY2hlZFZpZGVvSUQsIGNhY2hlZFZpZGVvVVJJLCBmcmFtZSwgaGVpZ2h0LCBzaG93Q29udHJvbHMsIHN0cmVhbVZpZGVvVVJJLCB0b3VjaENhbGxiYWNrLCB2aWRlb0VsLCB3aWR0aCwgeCwgeTsKCiAgICAgIHZpZGVvRWwgPSBkb2N1bWVudC5nZXRFbGVtZW50QnlJZChkaXZJZCk7CiAgICAgIGlmICh2aWRlb0VsICE9IG51bGwpIHsKICAgICAgICBmcmFtZSA9IHRoaXMuY2FsY3VsYXRlRGl2UG9zaXRpb24oZGl2SWQpOwogICAgICAgIGlmICh0aW1pbmdDYWxsYmFjayAhPSBudWxsKSB7CiAgICAgICAgICB0aGlzLnNldFRpbWluZ0NhbGxiYWNrKHRpbWluZ0NhbGxiYWNrKTsKICAgICAgICB9CiAgICAgICAgeCA9IGZyYW1lWyd4J107CiAgICAgICAgeSA9IGZyYW1lWyd5J107CiAgICAgICAgd2lkdGggPSBmcmFtZVsnd2lkdGgnXTsKICAgICAgICBoZWlnaHQgPSBmcmFtZVsnaGVpZ2h0J107CiAgICAgICAgYm9keVdpZHRoID0gZG9jdW1lbnQuYm9keS5jbGllbnRXaWR0aDsKICAgICAgICBib2R5SGVpZ2h0ID0gZG9jdW1lbnQuYm9keS5jbGllbnRIZWlnaHQ7CiAgICAgICAgY2FjaGVkVmlkZW9VUkkgPSB2aWRlb0VsLmdldEF0dHJpYnV0ZSgiY2FjaGVkVmlkZW9VUkkiKTsKICAgICAgICBjYWNoZWRWaWRlb0lEID0gdmlkZW9FbC5nZXRBdHRyaWJ1dGUoImNhY2hlZFZpZGVvSUQiKTsKICAgICAgICB0b3VjaENhbGxiYWNrID0gdmlkZW9FbC5nZXRBdHRyaWJ1dGUoIm9uVG91Y2giKTsKICAgICAgICBzdHJlYW1WaWRlb1VSSSA9IHZpZGVvRWwuZ2V0QXR0cmlidXRlKCJzdHJlYW1WaWRlb1VSSSIpOwogICAgICAgIGF1dG9QbGF5ID0gdmlkZW9FbC5nZXRBdHRyaWJ1dGUoImF1dG9QbGF5Iik7CiAgICAgICAgc2hvd0NvbnRyb2xzID0gdmlkZW9FbC5nZXRBdHRyaWJ1dGUoInNob3dDb250cm9scyIpOwogICAgICAgIGlmIChjYWNoZWRWaWRlb1VSSSB8fCBzdHJlYW1WaWRlb1VSSSkgewogICAgICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiaW5zZXJ0VmlkZW8iLCB7CiAgICAgICAgICAgIHg6IHgsCiAgICAgICAgICAgIHk6IHksCiAgICAgICAgICAgIHdpZHRoOiB3aWR0aCwKICAgICAgICAgICAgaGVpZ2h0OiBoZWlnaHQsCiAgICAgICAgICAgIGJvZHlXaWR0aDogYm9keVdpZHRoLAogICAgICAgICAgICBib2R5SGVpZ2h0OiBib2R5SGVpZ2h0LAogICAgICAgICAgICBjYWNoZWRWaWRlb1VSSTogY2FjaGVkVmlkZW9VUkksCiAgICAgICAgICAgIHN0cmVhbVZpZGVvVVJJOiBzdHJlYW1WaWRlb1VSSSwKICAgICAgICAgICAgdG91Y2hDYWxsYmFjazogdG91Y2hDYWxsYmFjaywKICAgICAgICAgICAgY2FjaGVkVmlkZW9JRDogY2FjaGVkVmlkZW9JRCwKICAgICAgICAgICAgYXV0b1BsYXk6IGF1dG9QbGF5LAogICAgICAgICAgICBzaG93Q29udHJvbHM6IHNob3dDb250cm9scywKICAgICAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgICAgICB9KTsKICAgICAgICB9IGVsc2UgewogICAgICAgICAgcmV0dXJuIGNhbGxiYWNrKHsKICAgICAgICAgICAgInJlc3VsdCI6IDAsCiAgICAgICAgICAgICJyZXNwb25zZSI6ICJjYWNoZWRWaWRlb1VSSSBvciBzdHJlYW1WaWRlb1VSSSBub3QgZm91bmQiLAogICAgICAgICAgICAiY2xhc3MiOiAiTU1JbmxpbmVWaWRlbyIsCiAgICAgICAgICAgICJjYWxsIjogImluc2VydFZpZGVvIgogICAgICAgICAgfSk7CiAgICAgICAgfQogICAgICB9IGVsc2UgewogICAgICAgIHJldHVybiBjYWxsYmFjayh7CiAgICAgICAgICAicmVzdWx0IjogMCwKICAgICAgICAgICJyZXNwb25zZSI6ICJEaXYgSWQgbm90IGZvdW5kIiwKICAgICAgICAgICJjbGFzcyI6ICJNTUlubGluZVZpZGVvIiwKICAgICAgICAgICJjYWxsIjogImluc2VydFZpZGVvIgogICAgICAgIH0pOwogICAgICB9CiAgICB9OwoKICAgIE1NSW5saW5lVmlkZW8ucHJvdG90eXBlLmluc2VydFZpZGVvID0gZnVuY3Rpb24odGltaW5nQ2FsbGJhY2ssIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmluc2VydFZpZGVvV2l0aElkKCdpbmxpbmVWaWRlbycsIHRpbWluZ0NhbGxiYWNrLCBjYWxsYmFjayk7CiAgICB9OwoKICAgIE1NSW5saW5lVmlkZW8ucHJvdG90eXBlLmNhbGN1bGF0ZURpdlBvc2l0aW9uID0gZnVuY3Rpb24oZGl2SWQpIHsKICAgICAgdmFyIGRpdkVsLCBoZWlnaHQsIHBvc2l0aW9uLCB3aWR0aCwgeCwgeTsKCiAgICAgIGRpdkVsID0gZG9jdW1lbnQuZ2V0RWxlbWVudEJ5SWQoZGl2SWQpOwogICAgICBwb3NpdGlvbiA9IHRoaXMudXRpbHMub2Zmc2V0KGRpdkVsKTsKICAgICAgeCA9IHBvc2l0aW9uWzBdOwogICAgICB5ID0gcG9zaXRpb25bMV07CiAgICAgIHdpZHRoID0gZGl2RWwub2Zmc2V0V2lkdGg7CiAgICAgIGhlaWdodCA9IGRpdkVsLm9mZnNldEhlaWdodDsKICAgICAgcmV0dXJuIHsKICAgICAgICB4OiB4LAogICAgICAgIHk6IHksCiAgICAgICAgd2lkdGg6IHdpZHRoLAogICAgICAgIGhlaWdodDogaGVpZ2h0CiAgICAgIH07CiAgICB9OwoKICAgIHJldHVybiBNTUlubGluZVZpZGVvOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgTU1DYWNoZWRWaWRlbyA9IChmdW5jdGlvbihfc3VwZXIpIHsKICAgIF9fZXh0ZW5kcyhNTUNhY2hlZFZpZGVvLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NQ2FjaGVkVmlkZW8oKSB7CiAgICAgIF9yZWY3ID0gTU1DYWNoZWRWaWRlby5fX3N1cGVyX18uY29uc3RydWN0b3IuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIF9yZWY3OwogICAgfQoKICAgIE1NQ2FjaGVkVmlkZW8udGltaW5nQ2FsbGJhY2sgPSBudWxsOwoKICAgIE1NQ2FjaGVkVmlkZW8uZXJyb3JDYWxsYmFjayA9IG51bGw7CgogICAgTU1DYWNoZWRWaWRlby5wcm90b3R5cGUudXBkYXRlVmlkZW9TZWVrVGltZSA9IGZ1bmN0aW9uKGN1cnJlbnRTZWVrVGltZSkgewogICAgICBpZiAodGhpcy50aW1pbmdDYWxsYmFjayAhPSBudWxsKSB7CiAgICAgICAgcmV0dXJuIHRoaXMudGltaW5nQ2FsbGJhY2soY3VycmVudFNlZWtUaW1lKTsKICAgICAgfQogICAgfTsKCiAgICBNTUNhY2hlZFZpZGVvLnByb3RvdHlwZS5zZXRUaW1pbmdDYWxsYmFjayA9IGZ1bmN0aW9uKHRpbWluZ0NhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLnRpbWluZ0NhbGxiYWNrID0gdGltaW5nQ2FsbGJhY2s7CiAgICB9OwoKICAgIE1NQ2FjaGVkVmlkZW8ucHJvdG90eXBlLnNldEVycm9yID0gZnVuY3Rpb24oZXJyb3IpIHsKICAgICAgaWYgKHRoaXMuZXJyb3JDYWxsYmFjayAhPSBudWxsKSB7CiAgICAgICAgcmV0dXJuIHRoaXMuZXJyb3JDYWxsYmFjayhlcnJvcik7CiAgICAgIH0KICAgIH07CgogICAgTU1DYWNoZWRWaWRlby5wcm90b3R5cGUuc2V0RXJyb3JDYWxsYmFjayA9IGZ1bmN0aW9uKGVycm9yQ2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZXJyb3JDYWxsYmFjayA9IGVycm9yQ2FsbGJhY2s7CiAgICB9OwoKICAgIE1NQ2FjaGVkVmlkZW8ucHJvdG90eXBlLnJlc3RhcnRWaWRlbyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInJlc3RhcnRWaWRlbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NQ2FjaGVkVmlkZW8ucHJvdG90eXBlLmVuZFZpZGVvID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiZW5kVmlkZW8iLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUNhY2hlZFZpZGVvLnByb3RvdHlwZS5wYXVzZVZpZGVvID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgicGF1c2VWaWRlbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NQ2FjaGVkVmlkZW8ucHJvdG90eXBlLnBsYXlWaWRlbyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInBsYXlWaWRlbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NQ2FjaGVkVmlkZW8ucHJvdG90eXBlLmF2YWlsYWJsZUNhY2hlZFZpZGVvcyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImF2YWlsYWJsZUNhY2hlZFZpZGVvcyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NQ2FjaGVkVmlkZW8ucHJvdG90eXBlLnBsYXlDYWNoZWRWaWRlbyA9IGZ1bmN0aW9uKHZpZGVvSWQsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInBsYXlDYWNoZWRWaWRlbyIsIHsKICAgICAgICB2aWRlb0lkOiB2aWRlb0lkLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1DYWNoZWRWaWRlby5wcm90b3R5cGUuY2FjaGVWaWRlbyA9IGZ1bmN0aW9uKHVybCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiY2FjaGVWaWRlbyIsIHsKICAgICAgICB1cmw6IHVybCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NQ2FjaGVkVmlkZW8ucHJvdG90eXBlLnZpZGVvSWRFeGlzdHMgPSBmdW5jdGlvbih2aWRlb0lkLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJ2aWRlb0lkRXhpc3RzIiwgewogICAgICAgIHZpZGVvSWQ6IHZpZGVvSWQsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICByZXR1cm4gTU1DYWNoZWRWaWRlbzsKCiAgfSkoTU1CcmlkZ2VPYmplY3QpOwogIE1NSW50ZXJzdGl0aWFsID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NSW50ZXJzdGl0aWFsLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NSW50ZXJzdGl0aWFsKCkgewogICAgICBfcmVmOCA9IE1NSW50ZXJzdGl0aWFsLl9fc3VwZXJfXy5jb25zdHJ1Y3Rvci5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gX3JlZjg7CiAgICB9CgogICAgTU1JbnRlcnN0aXRpYWwuYW5pbWF0aW9uVHlwZXMgPSB7CiAgICAgICJpb3MiOiBbImN1cmwiLCAiZmxpcCIsICJkaXNzb2x2ZSIsICJzbGlkZXVwIiwgIm5vbmUiXSwKICAgICAgImFuZHJvaWQiOiBbInNsaWRldXAiLCAic2xpZGVkb3duIiwgImV4cGxvZGUiLCAibm9uZSJdLAogICAgICAid2luZG93cyI6IFsic2xpZGV1cCIsICJzbGlkZWRvd24iLCAiZXhwbG9kZSIsICJub25lIl0KICAgIH07CgogICAgTU1JbnRlcnN0aXRpYWwucHJvdG90eXBlLmNsb3NlID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiY2xvc2UiLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUludGVyc3RpdGlhbC5wcm90b3R5cGUub3BlbiA9IGZ1bmN0aW9uKHVybCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgib3BlbiIsIHsKICAgICAgICB1cmw6IHVybCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NSW50ZXJzdGl0aWFsLnByb3RvdHlwZS51c2VDdXN0b21DbG9zZSA9IGZ1bmN0aW9uKHVzZUN1c3RvbUNsb3NlLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJ1c2VDdXN0b21DbG9zZSIsIHsKICAgICAgICB1c2VDdXN0b21DbG9zZTogdXNlQ3VzdG9tQ2xvc2UsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUludGVyc3RpdGlhbC5wcm90b3R5cGUuc2V0T3JpZW50YXRpb24gPSBmdW5jdGlvbihwcm9wZXJ0aWVzLCBjYWxsYmFjaykgewogICAgICBwcm9wZXJ0aWVzWyJjYWxsYmFjayJdID0gY2FsbGJhY2s7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInNldE9yaWVudGF0aW9uIiwgcHJvcGVydGllcyk7CiAgICB9OwoKICAgIE1NSW50ZXJzdGl0aWFsLnByb3RvdHlwZS5leHBhbmRUb0V4dGVybmFsQnJvd3NlciA9IGZ1bmN0aW9uKHVybCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiZXhwYW5kVG9FeHRlcm5hbEJyb3dzZXIiLCB7CiAgICAgICAgdXJsOiB1cmwsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTUludGVyc3RpdGlhbC5wcm90b3R5cGUuZXhwYW5kV2l0aFByb3BlcnRpZXMgPSBmdW5jdGlvbih1cmwsIHByb3BlcnRpZXMsIGNhbGxiYWNrKSB7CiAgICAgIHZhciBrZXksIHBhcmFtcywgdHJhbnNpdGlvblR5cGUsIHZhbHVlOwoKICAgICAgcGFyYW1zID0gewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9OwogICAgICBpZiAodXJsICE9IG51bGwpIHsKICAgICAgICBwYXJhbXNbInVybCJdID0gdXJsOwogICAgICB9CiAgICAgIE1NSlMudXRpbHMuY29uc29sZUxvZygiZXhwYW5kV2l0aFByb3BlcnRpZXMgcHJvcGVydGllcyAiICsgSlNPTi5zdHJpbmdpZnkocHJvcGVydGllcykpOwogICAgICBpZiAocHJvcGVydGllcyAhPSBudWxsKSB7CiAgICAgICAgZm9yIChrZXkgaW4gcHJvcGVydGllcykgewogICAgICAgICAgaWYgKCFfX2hhc1Byb3AuY2FsbChwcm9wZXJ0aWVzLCBrZXkpKSBjb250aW51ZTsKICAgICAgICAgIHZhbHVlID0gcHJvcGVydGllc1trZXldOwogICAgICAgICAgaWYgKGtleSA9PT0gInRyYW5zaXRpb24iKSB7CiAgICAgICAgICAgIHRyYW5zaXRpb25UeXBlID0gdmFsdWU7CiAgICAgICAgICAgIHBhcmFtc1trZXldID0gdHJhbnNpdGlvblR5cGU7CiAgICAgICAgICB9IGVsc2UgewogICAgICAgICAgICBwYXJhbXNba2V5XSA9IHZhbHVlOwogICAgICAgICAgfQogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJleHBhbmRXaXRoUHJvcGVydGllcyIsIHBhcmFtcyk7CiAgICB9OwoKICAgIHJldHVybiBNTUludGVyc3RpdGlhbDsKCiAgfSkoTU1CcmlkZ2VPYmplY3QpOwogIE1NQnJhbmQgPSAoZnVuY3Rpb24oX3N1cGVyKSB7CiAgICBfX2V4dGVuZHMoTU1CcmFuZCwgX3N1cGVyKTsKCiAgICBmdW5jdGlvbiBNTUJyYW5kKCkgewogICAgICBfcmVmOSA9IE1NQnJhbmQuX19zdXBlcl9fLmNvbnN0cnVjdG9yLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIHJldHVybiBfcmVmOTsKICAgIH0KCiAgICBNTUJyYW5kLnByb3RvdHlwZS5nZXRJbmZvID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiZ2V0SW5mbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIHJldHVybiBNTUJyYW5kOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgTU1BcHBTdG9yZSA9IChmdW5jdGlvbihfc3VwZXIpIHsKICAgIF9fZXh0ZW5kcyhNTUFwcFN0b3JlLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NQXBwU3RvcmUoKSB7CiAgICAgIF9yZWYxMCA9IE1NQXBwU3RvcmUuX19zdXBlcl9fLmNvbnN0cnVjdG9yLmFwcGx5KHRoaXMsIGFyZ3VtZW50cyk7CiAgICAgIHJldHVybiBfcmVmMTA7CiAgICB9CgogICAgTU1BcHBTdG9yZS5wcm90b3R5cGUubG9hZEFwcCA9IGZ1bmN0aW9uKGFwcElkLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJsb2FkQXBwIiwgewogICAgICAgIGFwcElkOiBhcHBJZCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIHJldHVybiBNTUFwcFN0b3JlOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgTU1QYXN0ZWJvYXJkID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NUGFzdGVib2FyZCwgX3N1cGVyKTsKCiAgICBmdW5jdGlvbiBNTVBhc3RlYm9hcmQoKSB7CiAgICAgIF9yZWYxMSA9IE1NUGFzdGVib2FyZC5fX3N1cGVyX18uY29uc3RydWN0b3IuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIF9yZWYxMTsKICAgIH0KCiAgICBNTVBhc3RlYm9hcmQucHJvdG90eXBlLmdldFBhc3RlYm9hcmRDb250ZW50cyA9IGZ1bmN0aW9uKHBhc3RlYm9hcmRJZCwgY2FsbGJhY2spIHsKICAgICAgdmFyIGFyZ3M7CgogICAgICBhcmdzID0gewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9OwogICAgICBpZiAocGFzdGVib2FyZElkICE9IG51bGwpIHsKICAgICAgICBhcmdzWyJwYXN0ZWJvYXJkSWQiXSA9IHBhc3RlYm9hcmRJZDsKICAgICAgfQogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJnZXRQYXN0ZWJvYXJkQ29udGVudHMiLCBhcmdzKTsKICAgIH07CgogICAgTU1QYXN0ZWJvYXJkLnByb3RvdHlwZS53cml0ZVRvUGFzdGVib2FyZCA9IGZ1bmN0aW9uKGRhdGEsIHBhc3RlYm9hcmRJZCwgY2FsbGJhY2spIHsKICAgICAgdmFyIGFyZ3M7CgogICAgICBhcmdzID0gewogICAgICAgIGRhdGE6IGRhdGEsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH07CiAgICAgIGlmIChwYXN0ZWJvYXJkSWQgIT0gbnVsbCkgewogICAgICAgIGFyZ3NbInBhc3RlYm9hcmRJZCJdID0gcGFzdGVib2FyZElkOwogICAgICB9CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoIndyaXRlVG9QYXN0ZWJvYXJkIiwgYXJncyk7CiAgICB9OwoKICAgIHJldHVybiBNTVBhc3RlYm9hcmQ7CgogIH0pKE1NQnJpZGdlT2JqZWN0KTsKICBNTVBhc3Nib29rID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NUGFzc2Jvb2ssIF9zdXBlcik7CgogICAgZnVuY3Rpb24gTU1QYXNzYm9vaygpIHsKICAgICAgX3JlZjEyID0gTU1QYXNzYm9vay5fX3N1cGVyX18uY29uc3RydWN0b3IuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIF9yZWYxMjsKICAgIH0KCiAgICBNTVBhc3Nib29rLnByb3RvdHlwZS5pc1Bhc3Nib29rQXZhaWxhYmxlID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiaXNQYXNzYm9va0F2YWlsYWJsZSIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NUGFzc2Jvb2sucHJvdG90eXBlLmFkZFBhc3NGcm9tVVJMID0gZnVuY3Rpb24odXJsLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJhZGRQYXNzRnJvbVVSTCIsIHsKICAgICAgICB1cmw6IHVybCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NUGFzc2Jvb2sucHJvdG90eXBlLmlzUGFzc0luc3RhbGxlZCA9IGZ1bmN0aW9uKHVybCwgaWRlbnRpZmllciwgc2VyaWFsLCBjYWxsYmFjaykgewogICAgICBpZiAodXJsICE9IG51bGwpIHsKICAgICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJpc1Bhc3NJbnN0YWxsZWQiLCB7CiAgICAgICAgICB1cmw6IHVybCwKICAgICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICAgIH0pOwogICAgICB9IGVsc2UgewogICAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImlzUGFzc0luc3RhbGxlZCIsIHsKICAgICAgICAgIGlkZW50aWZpZXI6IGlkZW50aWZpZXIsCiAgICAgICAgICBzZXJpYWw6IHNlcmlhbCwKICAgICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICAgIH0pOwogICAgICB9CiAgICB9OwoKICAgIE1NUGFzc2Jvb2sucHJvdG90eXBlLmlzUGFzc1VSTEluc3RhbGxlZCA9IGZ1bmN0aW9uKHVybCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuaXNQYXNzSW5zdGFsbGVkKHVybCwgbnVsbCwgbnVsbCwgY2FsbGJhY2spOwogICAgfTsKCiAgICBNTVBhc3Nib29rLnByb3RvdHlwZS5pc1Bhc3NJZGVudGlmaWVySW5zdGFsbGVkID0gZnVuY3Rpb24oaWRlbnRpZmllciwgc2VyaWFsLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5pc1Bhc3NJbnN0YWxsZWQobnVsbCwgaWRlbnRpZmllciwgc2VyaWFsLCBjYWxsYmFjayk7CiAgICB9OwoKICAgIHJldHVybiBNTVBhc3Nib29rOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgTU1Tb2NpYWwgPSAoZnVuY3Rpb24oX3N1cGVyKSB7CiAgICBfX2V4dGVuZHMoTU1Tb2NpYWwsIF9zdXBlcik7CgogICAgZnVuY3Rpb24gTU1Tb2NpYWwoKSB7CiAgICAgIF9yZWYxMyA9IE1NU29jaWFsLl9fc3VwZXJfXy5jb25zdHJ1Y3Rvci5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gX3JlZjEzOwogICAgfQoKICAgIE1NU29jaWFsLnByb3RvdHlwZS50d2VldCA9IGZ1bmN0aW9uKG1lc3NhZ2UsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInR3ZWV0IiwgewogICAgICAgIG1lc3NhZ2U6IG1lc3NhZ2UsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTVNvY2lhbC5wcm90b3R5cGUudHdlZXRXaXRoQ29udGVudCA9IGZ1bmN0aW9uKG1lc3NhZ2UsIHVybHMsIGltYWdlcywgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgidHdlZXQiLCB7CiAgICAgICAgbWVzc2FnZTogbWVzc2FnZSwKICAgICAgICAidXJscyI6IHVybHMuam9pbignLCcpLAogICAgICAgICJpbWFnZXMiOiBpbWFnZXMuam9pbignLCcpLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1Tb2NpYWwucHJvdG90eXBlLmZhY2Vib29rUG9zdCA9IGZ1bmN0aW9uKG1lc3NhZ2UsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImZhY2Vib29rUG9zdCIsIHsKICAgICAgICBtZXNzYWdlOiBtZXNzYWdlLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1Tb2NpYWwucHJvdG90eXBlLmZhY2Vib29rUG9zdFdpdGhDb250ZW50ID0gZnVuY3Rpb24obWVzc2FnZSwgdXJscywgaW1hZ2VzLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJmYWNlYm9va1Bvc3QiLCB7CiAgICAgICAgbWVzc2FnZTogbWVzc2FnZSwKICAgICAgICAidXJscyI6IHVybHMuam9pbignLCcpLAogICAgICAgICJpbWFnZXMiOiBpbWFnZXMuam9pbignLCcpLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1Tb2NpYWwucHJvdG90eXBlLmF1dGhlbnRpY2F0ZWRTZXJ2aWNlcyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImF1dGhlbnRpY2F0ZWRTZXJ2aWNlcyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIHJldHVybiBNTVNvY2lhbDsKCiAgfSkoTU1CcmlkZ2VPYmplY3QpOwogIE1NU3BlZWNoa2l0ID0gKGZ1bmN0aW9uKF9zdXBlcikgewogICAgX19leHRlbmRzKE1NU3BlZWNoa2l0LCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NU3BlZWNoa2l0KCkgewogICAgICBfcmVmMTQgPSBNTVNwZWVjaGtpdC5fX3N1cGVyX18uY29uc3RydWN0b3IuYXBwbHkodGhpcywgYXJndW1lbnRzKTsKICAgICAgcmV0dXJuIF9yZWYxNDsKICAgIH0KCiAgICBNTVNwZWVjaGtpdC5wcm90b3R5cGUuc3RhcnRSZWNvcmRpbmcgPSBmdW5jdGlvbihsYW5ndWFnZSwgcmVjb2duaXplciwgZW5kT2ZTcGVlY2gsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInN0YXJ0UmVjb3JkaW5nIiwgewogICAgICAgIGxhbmd1YWdlOiBsYW5ndWFnZSwKICAgICAgICByZWNvZ25pemVyOiByZWNvZ25pemVyLAogICAgICAgIGVuZE9mU3BlZWNoOiBlbmRPZlNwZWVjaCwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NU3BlZWNoa2l0LnByb3RvdHlwZS5lbmRSZWNvcmRpbmcgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJlbmRSZWNvcmRpbmciLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTVNwZWVjaGtpdC5wcm90b3R5cGUuc2FtcGxlQmFja2dyb3VuZEF1ZGlvTGV2ZWwgPSBmdW5jdGlvbihjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJzYW1wbGVCYWNrZ3JvdW5kQXVkaW9MZXZlbCIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NU3BlZWNoa2l0LnByb3RvdHlwZS50ZXh0VG9TcGVlY2ggPSBmdW5jdGlvbihsYW5ndWFnZSwgdGV4dCwgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgidGV4dFRvU3BlZWNoIiwgewogICAgICAgIGxhbmd1YWdlOiBsYW5ndWFnZSwKICAgICAgICB0ZXh0OiB0ZXh0LAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1TcGVlY2hraXQucHJvdG90eXBlLnJlbGVhc2VWb2ljZSA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIE1NSlMuc2RrLnNwZWVjaFJlc3VsdHMgPSBbXTsKICAgICAgTU1KUy5zZGsuc3BlZWNoQXVkaW9MZXZlbCA9IDA7CiAgICAgIE1NSlMuc2RrLnNwZWVjaEJhY2tncm91bmRBdWRpb0xldmVsID0gMDsKICAgICAgTU1KUy5zZGsuc3BlZWNoU3RhdHVzID0gIlJlbGVhc2VkIjsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgicmVsZWFzZVZvaWNlIiwgewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1TcGVlY2hraXQucHJvdG90eXBlLmNhY2hlQXVkaW8gPSBmdW5jdGlvbih1cmwsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImNhY2hlQXVkaW8iLCB7CiAgICAgICAgdXJsOiB1cmwsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTVNwZWVjaGtpdC5wcm90b3R5cGUucGxheUF1ZGlvID0gZnVuY3Rpb24odXJsLCBwcm9wZXJ0aWVzLCBjYWxsYmFjaykgewogICAgICBwcm9wZXJ0aWVzWyJ1cmwiXSA9IHVybDsKICAgICAgcHJvcGVydGllc1siY2FsbGJhY2siXSA9IGNhbGxiYWNrOwogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJwbGF5QXVkaW8iLCBwcm9wZXJ0aWVzKTsKICAgIH07CgogICAgTU1TcGVlY2hraXQucHJvdG90eXBlLnN0b3BBdWRpbyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInN0b3BBdWRpbyIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NU3BlZWNoa2l0LnByb3RvdHlwZS5hZGRDdXN0b21Wb2ljZVdvcmRzID0gZnVuY3Rpb24od29yZHMsIGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImFkZEN1c3RvbVZvaWNlV29yZHMiLCB7CiAgICAgICAgd29yZHM6IHdvcmRzLAogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1TcGVlY2hraXQucHJvdG90eXBlLmRlbGV0ZUN1c3RvbVZvaWNlV29yZHMgPSBmdW5jdGlvbih3b3JkcywgY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiZGVsZXRlQ3VzdG9tVm9pY2VXb3JkcyIsIHsKICAgICAgICB3b3Jkczogd29yZHMsCiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTVNwZWVjaGtpdC5wcm90b3R5cGUuZ2V0U2Vzc2lvbklkID0gZnVuY3Rpb24oY2FsbGJhY2spIHsKICAgICAgcmV0dXJuIHRoaXMuZW5xdWV1ZSgiZ2V0U2Vzc2lvbklkIiwgewogICAgICAgIGNhbGxiYWNrOiBjYWxsYmFjawogICAgICB9KTsKICAgIH07CgogICAgTU1TcGVlY2hraXQucHJvdG90eXBlLmdldFJlY29nbml0aW9uUmVzdWx0cyA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gTU1KUy5zZGsuc3BlZWNoUmVzdWx0czsKICAgIH07CgogICAgTU1TcGVlY2hraXQucHJvdG90eXBlLmdldEJhY2tncm91bmROb2lzZUxldmVsID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBNTUpTLnNkay5zcGVlY2hCYWNrZ3JvdW5kQXVkaW9MZXZlbDsKICAgIH07CgogICAgTU1TcGVlY2hraXQucHJvdG90eXBlLmdldEF1ZGlvTGV2ZWwgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMuc2RrLnNwZWVjaEF1ZGlvTGV2ZWw7CiAgICB9OwoKICAgIE1NU3BlZWNoa2l0LnByb3RvdHlwZS5nZXRWb2ljZVN0YXRlID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBNTUpTLnNkay5zcGVlY2hTdGF0dXM7CiAgICB9OwoKICAgIE1NU3BlZWNoa2l0LnByb3RvdHlwZS5nZXRBdWRpb1Bvc2l0aW9uID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBNTUpTLnNkay5hdWRpb1Bvc2l0aW9uOwogICAgfTsKCiAgICByZXR1cm4gTU1TcGVlY2hraXQ7CgogIH0pKE1NQnJpZGdlT2JqZWN0KTsKICBNTU1pY3JvcGhvbmUgPSAoZnVuY3Rpb24oX3N1cGVyKSB7CiAgICBfX2V4dGVuZHMoTU1NaWNyb3Bob25lLCBfc3VwZXIpOwoKICAgIGZ1bmN0aW9uIE1NTWljcm9waG9uZSgpIHsKICAgICAgX3JlZjE1ID0gTU1NaWNyb3Bob25lLl9fc3VwZXJfXy5jb25zdHJ1Y3Rvci5hcHBseSh0aGlzLCBhcmd1bWVudHMpOwogICAgICByZXR1cm4gX3JlZjE1OwogICAgfQoKICAgIE1NTWljcm9waG9uZS5wcm90b3R5cGUuc3RhcnRSZWNvcmRpbmcgPSBmdW5jdGlvbihwYXRoLCBkdXJhdGlvbiwgY2FsbGJhY2tSYXRlLCBjYWxsYmFjaykgewogICAgICByZXR1cm4gdGhpcy5lbnF1ZXVlKCJzdGFydFJlY29yZGluZyIsIHsKICAgICAgICBwYXRoOiBwYXRoLAogICAgICAgIGR1cmF0aW9uOiBkdXJhdGlvbiwKICAgICAgICBjYWxsYmFja1JhdGU6IGNhbGxiYWNrUmF0ZSwKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NTWljcm9waG9uZS5wcm90b3R5cGUuc3RvcFJlY29yZGluZyA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoInN0b3BSZWNvcmRpbmciLCB7CiAgICAgICAgY2FsbGJhY2s6IGNhbGxiYWNrCiAgICAgIH0pOwogICAgfTsKCiAgICBNTU1pY3JvcGhvbmUucHJvdG90eXBlLmlzUmVjb3JkaW5nQWxsb3dlZCA9IGZ1bmN0aW9uKGNhbGxiYWNrKSB7CiAgICAgIHJldHVybiB0aGlzLmVucXVldWUoImlzUmVjb3JkaW5nQWxsb3dlZCIsIHsKICAgICAgICBjYWxsYmFjazogY2FsbGJhY2sKICAgICAgfSk7CiAgICB9OwoKICAgIE1NTWljcm9waG9uZS5wcm90b3R5cGUuZ2V0TWljcm9waG9uZUF1ZGlvTGV2ZWwgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMuc2RrLm1pY3JvcGhvbmVBdWRpb0xldmVsOwogICAgfTsKCiAgICBNTU1pY3JvcGhvbmUucHJvdG90eXBlLmdldE1pY3JvcGhvbmVTdGF0ZSA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gTU1KUy5zZGsubWljcm9waG9uZVN0YXRlOwogICAgfTsKCiAgICByZXR1cm4gTU1NaWNyb3Bob25lOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgTVJBSUQgPSAoZnVuY3Rpb24oX3N1cGVyKSB7CiAgICBfX2V4dGVuZHMoTVJBSUQsIF9zdXBlcik7CgogICAgZnVuY3Rpb24gTVJBSUQoKSB7CiAgICAgIHRoaXMuc2RrID0gTU1KUy5zZGs7CiAgICAgIHRoaXMudXRpbHMgPSBNTUpTLnV0aWxzOwogICAgICB0aGlzLnByb3BlcnRpZXMgPSB7CiAgICAgICAgd2lkdGg6IG51bGwsCiAgICAgICAgaGVpZ2h0OiBudWxsLAogICAgICAgIHVzZUN1c3RvbUNsb3NlOiBmYWxzZSwKICAgICAgICBpc01vZGFsOiB0cnVlCiAgICAgIH07CiAgICAgIHRoaXMub3JpZW50YXRpb25Qcm9wZXJ0aWVzID0gewogICAgICAgIGFsbG93T3JpZW50YXRpb25DaGFuZ2U6IHRydWUsCiAgICAgICAgZm9yY2VPcmllbnRhdGlvbjogJ25vbmUnCiAgICAgIH07CiAgICAgIHRoaXMucmVzaXplUHJvcGVydGllcyA9IHsKICAgICAgICB3aWR0aDogbnVsbCwKICAgICAgICBoZWlnaHQ6IG51bGwsCiAgICAgICAgY3VzdG9tQ2xvc2VQb3NpdGlvbjogJ3RvcC1yaWdodCcsCiAgICAgICAgb2Zmc2V0WDogMCwKICAgICAgICBvZmZzZXRZOiAwLAogICAgICAgIGFsbG93T2Zmc2NyZWVuOiB0cnVlCiAgICAgIH07CiAgICAgIHRoaXMuYXVkaW9Qcm9wZXJ0aWVzID0gewogICAgICAgIGxvb3A6IGZhbHNlLAogICAgICAgIGNvbnRyb2xzOiBmYWxzZQogICAgICB9OwogICAgfQoKICAgIE1SQUlELnByb3RvdHlwZS5nZXRBZFNpemUgPSBmdW5jdGlvbigpIHsKICAgICAgaWYgKHRoaXMuc2RrLmFkU2l6ZSAhPSBudWxsKSB7CiAgICAgICAgdGhpcy51dGlscy5jb25zb2xlTG9nKCJNUkFJRCBnZXRBZFNpemUgIiArIEpTT04uc3RyaW5naWZ5KHRoaXMuc2RrLmFkU2l6ZSkpOwogICAgICAgIGlmICh0aGlzLnNkay5hZFNpemVbImhlaWdodCJdID4gMCAmJiB0aGlzLnNkay5hZFNpemVbIndpZHRoIl0gPiAwKSB7CiAgICAgICAgICByZXR1cm4gdGhpcy5zZGsuYWRTaXplOwogICAgICAgIH0KICAgICAgfQogICAgICByZXR1cm4gbnVsbDsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmNhbGxiYWNrTWFuYWdlciA9IGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgIHZhciBrbGFzcywgbWV0aG9kLCByZXNwb25zZV9kYXRhLCByZXN1bHQ7CgogICAgICByZXN1bHQgPSByZXNwb25zZVsncmVzdWx0J107CiAgICAgIG1ldGhvZCA9IHJlc3BvbnNlWydjYWxsJ107CiAgICAgIHJlc3BvbnNlX2RhdGEgPSByZXNwb25zZVsncmVzcG9uc2UnXTsKICAgICAga2xhc3MgPSByZXNwb25zZVsnY2xhc3MnXTsKICAgICAgcmV0dXJuIHRoaXM7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5nZXRWZXJzaW9uID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiAiMi4wIjsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmNsb3NlID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBNTUpTLmludGVyc3RpdGlhbC5jbG9zZSgoZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICBpZiAocmVzcG9uc2VbJ3Jlc3VsdCddIDwgMSkgewogICAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygiZXJyb3IiLCAiQ2xvc2UgZmFpbGVkIiwgImNsb3NlIik7CiAgICAgICAgfQogICAgICB9KSk7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5leHBhbmQgPSBmdW5jdGlvbihfdXJsKSB7CiAgICAgIHZhciBrLCBtYXhTaXplLCBwcm9wcywgdiwgX3JlZjE2OwoKICAgICAgdGhpcy51dGlscy5jb25zb2xlTG9nKCdtcmFpZC5leHBhbmQgY2FsbGVkIHdpdGggcHJvcGVydGllczogJyArIEpTT04uc3RyaW5naWZ5KHRoaXMuZ2V0RXhwYW5kUHJvcGVydGllcygpKSk7CiAgICAgIHRoaXMudXRpbHMuY29uc29sZUxvZygnbXJhaWQuZXhwYW5kIHVybDogJyArIF91cmwpOwogICAgICBwcm9wcyA9IHRoaXMuZ2V0RXhwYW5kUHJvcGVydGllcygpOwogICAgICBtYXhTaXplID0gdGhpcy5nZXRNYXhTaXplKCk7CiAgICAgIGlmICgocHJvcHMgIT0gbnVsbCkgJiYgKG1heFNpemUgIT0gbnVsbCkpIHsKICAgICAgICBpZiAocHJvcHNbImhlaWdodCJdID09PSBtYXhTaXplWyJoZWlnaHQiXSAmJiBwcm9wc1sid2lkdGgiXSA9PT0gbWF4U2l6ZVsid2lkdGgiXSkgewogICAgICAgICAgcHJvcHNbImhlaWdodCJdID0gdm9pZCAwOwogICAgICAgICAgcHJvcHNbIndpZHRoIl0gPSB2b2lkIDA7CiAgICAgICAgfQogICAgICB9CiAgICAgIF9yZWYxNiA9IHRoaXMub3JpZW50YXRpb25Qcm9wZXJ0aWVzOwogICAgICBmb3IgKGsgaW4gX3JlZjE2KSB7CiAgICAgICAgdiA9IF9yZWYxNltrXTsKICAgICAgICBwcm9wc1trXSA9IHY7CiAgICAgIH0KICAgICAgcmV0dXJuIE1NSlMuaW50ZXJzdGl0aWFsLmV4cGFuZFdpdGhQcm9wZXJ0aWVzKF91cmwsIHByb3BzLCAoZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICBpZiAocmVzcG9uc2VbJ3Jlc3VsdCddIDwgMSkgewogICAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygiZXJyb3IiLCAiRXhwYW5kIGZhaWxlZCIsICJleHBhbmQiKTsKICAgICAgICB9CiAgICAgIH0pKTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLm9wZW4gPSBmdW5jdGlvbihfdXJsKSB7CiAgICAgIHJldHVybiBNTUpTLmludGVyc3RpdGlhbC5vcGVuKF91cmwsIChmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIGlmIChyZXNwb25zZVsncmVzdWx0J10gPCAxKSB7CiAgICAgICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJlcnJvciIsICJPcGVuIGZhaWxlZCB0byBvcGVuIGV4dGVybmFsIHVybCIsICJvcGVuIik7CiAgICAgICAgfQogICAgICB9KSk7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5nZXRFeHBhbmRQcm9wZXJ0aWVzID0gZnVuY3Rpb24oKSB7CiAgICAgIHZhciBtYXhTaXplOwoKICAgICAgbWF4U2l6ZSA9IHRoaXMuZ2V0TWF4U2l6ZSgpOwogICAgICBpZiAobWF4U2l6ZSAhPSBudWxsKSB7CiAgICAgICAgaWYgKHRoaXMucHJvcGVydGllc1siaGVpZ2h0Il0gPT09IG51bGwgfHwgdGhpcy5wcm9wZXJ0aWVzWyJoZWlnaHQiXSA9PT0gdm9pZCAwKSB7CiAgICAgICAgICB0aGlzLnByb3BlcnRpZXNbImhlaWdodCJdID0gbWF4U2l6ZVsiaGVpZ2h0Il07CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLnByb3BlcnRpZXNbIndpZHRoIl0gPT09IG51bGwgfHwgdGhpcy5wcm9wZXJ0aWVzWyJ3aWR0aCJdID09PSB2b2lkIDApIHsKICAgICAgICAgIHRoaXMucHJvcGVydGllc1sid2lkdGgiXSA9IG1heFNpemVbIndpZHRoIl07CiAgICAgICAgfQogICAgICAgIHJldHVybiB0aGlzLnByb3BlcnRpZXM7CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygiZXJyb3IiLCAiZ2V0RXhwYW5kUHJvcGVydGllcyBmYWlsZWQiLCAiZ2V0RXhwYW5kUHJvcGVydGllcyIpOwogICAgICB9CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5zZXRFeHBhbmRQcm9wZXJ0aWVzID0gZnVuY3Rpb24oX3Byb3BlcnRpZXMpIHsKICAgICAgdGhpcy51dGlscy5jb25zb2xlTG9nKCdzZXRFeHBhbmRQcm9wZXJ0aWVzOiAnICsgSlNPTi5zdHJpbmdpZnkodGhpcy5wcm9wZXJ0aWVzKSk7CiAgICAgIHJldHVybiB0aGlzLnByb3BlcnRpZXMgPSBfcHJvcGVydGllczsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmdldFBsYWNlbWVudFR5cGUgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIHRoaXMuc2RrLnBsYWNlbWVudFR5cGU7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5nZXRTdGF0ZSA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gdGhpcy5zZGsuc3RhdGU7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS51c2VDdXN0b21DbG9zZSA9IGZ1bmN0aW9uKF9jdXN0b21DbG9zZSkgewogICAgICB0aGlzLnByb3BlcnRpZXNbInVzZUN1c3RvbUNsb3NlIl0gPSBfY3VzdG9tQ2xvc2U7CiAgICAgIHRoaXMudXRpbHMuY29uc29sZUxvZygiVXNlIEN1c3RvbSBDbG9zZSB3YXMgY2FsbGVkOiAiICsgX2N1c3RvbUNsb3NlKTsKICAgICAgcmV0dXJuIE1NSlMuaW50ZXJzdGl0aWFsLnVzZUN1c3RvbUNsb3NlKF9jdXN0b21DbG9zZSwgKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgaWYgKHJlc3BvbnNlWydyZXN1bHQnXSA8IDEpIHsKICAgICAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoImVycm9yIiwgIlVzZSBjdXN0b20gY2xvc2UgZmFpbGVkIHRvIHNldCIsICJ1c2VDdXN0b21DbG9zZSIpOwogICAgICAgIH0KICAgICAgfSkpOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUuaXNWaWV3YWJsZSA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gdGhpcy5zZGsudmlld2FibGU7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5yZW1vdmVFdmVudExpc3RlbmVyID0gZnVuY3Rpb24oZXZlbnQsIGxpc3RlbmVyKSB7CiAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5yZW1vdmVFdmVudExpc3RlbmVyKGV2ZW50LCBsaXN0ZW5lcik7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5hZGRFdmVudExpc3RlbmVyID0gZnVuY3Rpb24oZXZlbnQsIGxpc3RlbmVyKSB7CiAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5hZGRFdmVudExpc3RlbmVyKGV2ZW50LCBsaXN0ZW5lcik7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5maXJlRXZlbnRDYWxsYmFja3MgPSBmdW5jdGlvbihldmVudE5hbWUsIHBhcmFtZXRlciwgYWN0aW9uKSB7CiAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoZXZlbnROYW1lLCBwYXJhbWV0ZXIsIGFjdGlvbik7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5yZXNpemUgPSBmdW5jdGlvbigpIHsKICAgICAgdmFyIGNhbGxlZHJlc2l6ZVByb3BlcnRpZXMsIG1heFNpemU7CgogICAgICBtYXhTaXplID0gdGhpcy5nZXRNYXhTaXplKCk7CiAgICAgIGNhbGxlZHJlc2l6ZVByb3BlcnRpZXMgPSB0aGlzLmdldFJlc2l6ZVByb3BlcnRpZXMoKTsKICAgICAgaWYgKGNhbGxlZHJlc2l6ZVByb3BlcnRpZXNbImFsbG93T2Zmc2NyZWVuIl0gPT09IGZhbHNlKSB7CiAgICAgICAgaWYgKGNhbGxlZHJlc2l6ZVByb3BlcnRpZXNbIndpZHRoIl0gPiBtYXhTaXplWyJ3aWR0aCJdIHx8IGNhbGxlZHJlc2l6ZVByb3BlcnRpZXNbImhlaWdodCJdID4gbWF4U2l6ZVsiaGVpZ2h0Il0pIHsKICAgICAgICAgIHRoaXMuZmlyZUV2ZW50Q2FsbGJhY2tzKCJlcnJvciIsICJSZXNpemUgaXMgdW5zdXBwb3J0ZWQgaW4gdGhpcyBhcHBsaWNhdGlvbi4iLCAicmVzaXplIik7CiAgICAgICAgICByZXR1cm47CiAgICAgICAgfQogICAgICB9CiAgICAgIE1NSlMuYmFubmVyLnJlc2l6ZShjYWxsZWRyZXNpemVQcm9wZXJ0aWVzLCAoZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICBpZiAocmVzcG9uc2VbJ3Jlc3VsdCddIDwgMSkgewogICAgICAgICAgcmV0dXJuIG1yYWlkLmZpcmVFdmVudENhbGxiYWNrcygiZXJyb3IiLCAiUmVzaXplIGlzIHVuc3VwcG9ydGVkIGluIHRoaXMgYXBwbGljYXRpb24uIiwgInJlc2l6ZSIpOwogICAgICAgIH0KICAgICAgfSkpOwogICAgICByZXR1cm4gbnVsbDsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmdldFJlc2l6ZVByb3BlcnRpZXMgPSBmdW5jdGlvbigpIHsKICAgICAgdmFyIGFkU2l6ZTsKCiAgICAgIGFkU2l6ZSA9IHRoaXMuZ2V0QWRTaXplKCk7CiAgICAgIGlmIChhZFNpemUgIT0gbnVsbCkgewogICAgICAgIE1NSlMudXRpbHMuY29uc29sZUxvZygiQWQgU2l6ZSB3YXMgZm91bmQiKTsKICAgICAgICBpZiAodGhpcy5yZXNpemVQcm9wZXJ0aWVzWyJoZWlnaHQiXSA9PT0gbnVsbCkgewogICAgICAgICAgdGhpcy5yZXNpemVQcm9wZXJ0aWVzWyJoZWlnaHQiXSA9IGFkU2l6ZVsiaGVpZ2h0Il07CiAgICAgICAgfQogICAgICAgIGlmICh0aGlzLnJlc2l6ZVByb3BlcnRpZXNbIndpZHRoIl0gPT09IG51bGwpIHsKICAgICAgICAgIHRoaXMucmVzaXplUHJvcGVydGllc1sid2lkdGgiXSA9IGFkU2l6ZVsid2lkdGgiXTsKICAgICAgICB9CiAgICAgICAgcmV0dXJuIHRoaXMucmVzaXplUHJvcGVydGllczsKICAgICAgfSBlbHNlIHsKICAgICAgICBNTUpTLnV0aWxzLmNvbnNvbGVMb2coImdldFJlc2l6ZVByb3BlcnRpZXMgZmFpbGVkIik7CiAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygiZXJyb3IiLCAiUmVzaXplIGlzIHVuc3VwcG9ydGVkIGluIHRoaXMgYXBwbGljYXRpb24uIiwgInJlc2l6ZSIpOwogICAgICB9CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5zZXRSZXNpemVQcm9wZXJ0aWVzID0gZnVuY3Rpb24oX3Byb3BlcnRpZXMpIHsKICAgICAgcmV0dXJuIHRoaXMucmVzaXplUHJvcGVydGllcyA9IF9wcm9wZXJ0aWVzOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUuZ2V0Q3VycmVudFBvc2l0aW9uID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLnNkay5hZFNpemU7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5nZXRNYXhTaXplID0gZnVuY3Rpb24oKSB7CiAgICAgIGlmICh0aGlzLnNkay5hZFByb3BlcnRpZXNbIm1heFNpemUiXSAhPSBudWxsKSB7CiAgICAgICAgcmV0dXJuIHsKICAgICAgICAgICJoZWlnaHQiOiB0aGlzLnNkay5hZFByb3BlcnRpZXNbIm1heFNpemUiXVsiaGVpZ2h0Il0sCiAgICAgICAgICAid2lkdGgiOiB0aGlzLnNkay5hZFByb3BlcnRpZXNbIm1heFNpemUiXVsid2lkdGgiXQogICAgICAgIH07CiAgICAgIH0gZWxzZSB7CiAgICAgICAgTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJlcnJvciIsICJnZXRSZXNpemVQcm9wZXJ0aWVzIGZhaWxlZCIsICJnZXRSZXNpemVQcm9wZXJ0aWVzIik7CiAgICAgIH0KICAgICAgcmV0dXJuIG51bGw7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5nZXREZWZhdWx0UG9zaXRpb24gPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIHRoaXMuc2RrLmRlZmF1bHRQb3NpdGlvbjsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmdldFNjcmVlblNpemUgPSBmdW5jdGlvbigpIHsKICAgICAgTU1KUy51dGlscy5jb25zb2xlTG9nKCJnZXRTY3JlZW5TaXplOiAiICsgdGhpcy5zZGsuYWRQcm9wZXJ0aWVzWyJzY3JlZW4iXSk7CiAgICAgIGlmICh0aGlzLnNkay5hZFByb3BlcnRpZXNbInNjcmVlbiJdICE9IG51bGwpIHsKICAgICAgICByZXR1cm4gdGhpcy5zZGsuYWRQcm9wZXJ0aWVzWyJzY3JlZW4iXTsKICAgICAgfSBlbHNlIHsKICAgICAgICB0aGlzLmZpcmVFdmVudENhbGxiYWNrcygiZXJyb3IiLCAiU2NyZWVuIHNpemUgaXMgdW5hdmFpbGFibGUiLCAiZ2V0U2NyZWVuU2l6ZSIpOwogICAgICB9CiAgICAgIHJldHVybiBudWxsOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUuc3VwcG9ydHMgPSBmdW5jdGlvbihmZWF0dXJlKSB7CiAgICAgIGlmIChmZWF0dXJlICE9IG51bGwpIHsKICAgICAgICByZXR1cm4gdGhpcy5zZGsuc3VwcG9ydFByb3BlcnRpZXNbZmVhdHVyZV07CiAgICAgIH0gZWxzZSB7CiAgICAgICAgcmV0dXJuIHRoaXMuc2RrLnN1cHBvcnRQcm9wZXJ0aWVzOwogICAgICB9CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5zdG9yZVBpY3R1cmUgPSBmdW5jdGlvbihVUkkpIHsKICAgICAgcmV0dXJuIE1NSlMubWVkaWEud3JpdGVUb1Bob3RvTGlicmFyeShVUkksICIiLCAiIiwgKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgaWYgKHJlc3BvbnNlWydyZXN1bHQnXSA8IDEpIHsKICAgICAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoImVycm9yIiwgIkVycm9yIHN0b3JpbmcgcGljdHVyZSIsICJzdG9yZVBpY3R1cmUiKTsKICAgICAgICB9CiAgICAgIH0pKTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmNyZWF0ZUNhbGVuZGFyRXZlbnQgPSBmdW5jdGlvbihwYXJhbWV0ZXJzKSB7CiAgICAgIHJldHVybiBNTUpTLmNhbGVuZGFyLmFkZEV2ZW50KHBhcmFtZXRlcnMsIChmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIGlmIChyZXNwb25zZVsncmVzdWx0J10gPCAxKSB7CiAgICAgICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJlcnJvciIsICJFcnJvciBhZGRpbmcgY2FsZW5kYXIgZXZlbnQiLCAiY3JlYXRlQ2FsZW5kYXJFdmVudCIpOwogICAgICAgIH0KICAgICAgfSkpOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUucGxheVZpZGVvID0gZnVuY3Rpb24oVVJJKSB7CiAgICAgIHJldHVybiBNTUpTLm1lZGlhLnBsYXlWaWRlbyhVUkksIChmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIGlmIChyZXNwb25zZVsncmVzdWx0J10gPCAxKSB7CiAgICAgICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJlcnJvciIsICJFcnJvciBwbGF5aW5nIHZpZGVvIiwgInBsYXlWaWRlbyIpOwogICAgICAgIH0KICAgICAgfSkpOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUuZ2V0T3JpZW50YXRpb25Qcm9wZXJ0aWVzID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiB0aGlzLm9yaWVudGF0aW9uUHJvcGVydGllczsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLnNldE9yaWVudGF0aW9uUHJvcGVydGllcyA9IGZ1bmN0aW9uKHByb3BlcnRpZXMpIHsKICAgICAgdGhpcy5vcmllbnRhdGlvblByb3BlcnRpZXMgPSBwcm9wZXJ0aWVzOwogICAgICBpZiAoKHRoaXMuZ2V0U3RhdGUoKSA9PT0gImV4cGFuZGVkIiAmJiB0aGlzLmdldFBsYWNlbWVudFR5cGUoKSA9PT0gImlubGluZSIpIHx8ICh0aGlzLmdldFBsYWNlbWVudFR5cGUoKSA9PT0gImludGVyc3RpdGlhbCIpKSB7CiAgICAgICAgcmV0dXJuIE1NSlMuaW50ZXJzdGl0aWFsLnNldE9yaWVudGF0aW9uKHRoaXMub3JpZW50YXRpb25Qcm9wZXJ0aWVzLCAibXJhaWQuY2FsbGJhY2tNYW5hZ2VyIik7CiAgICAgIH0KICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLnN0YXJ0UmVjb3JkaW5nID0gZnVuY3Rpb24obGFuZ3VhZ2VDb2RlKSB7CiAgICAgIHJldHVybiBNTUpTLnNwZWVjaGtpdC5zdGFydFJlY29yZGluZyhsYW5ndWFnZUNvZGUsICJkaWN0YXRpb24iLCAic2hvcnQiLCBmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIGlmIChyZXNwb25zZVsncmVzdWx0J10gPCAxKSB7CiAgICAgICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJ2b2ljZUVycm9yIiwgIlN0YXJ0IHJlY29yZGluZyBmYWlsZWQiLCAic3RhcnRSZWNvcmRpbmciKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUuZW5kUmVjb3JkaW5nID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBNTUpTLnNwZWVjaGtpdC5lbmRSZWNvcmRpbmcoZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICBpZiAocmVzcG9uc2VbJ3Jlc3VsdCddIDwgMSkgewogICAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygidm9pY2VFcnJvciIsICJFbmQgcmVjb3JkaW5nIGZhaWxlZCIsICJlbmRSZWNvcmRpbmciKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUudGV4dFRvU3BlZWNoID0gZnVuY3Rpb24odGV4dCwgbGFuZ3VhZ2VDb2RlKSB7CiAgICAgIHJldHVybiBNTUpTLnNwZWVjaGtpdC50ZXh0VG9TcGVlY2gobGFuZ3VhZ2VDb2RlLCB0ZXh0LCBmdW5jdGlvbihyZXNwb25zZSkgewogICAgICAgIGlmIChyZXNwb25zZVsncmVzdWx0J10gPCAxKSB7CiAgICAgICAgICByZXR1cm4gTU1KUy5saXN0ZW5lck1hbmFnZXIuZmlyZUV2ZW50Q2FsbGJhY2tzKCJ2b2ljZUVycm9yIiwgIlRleHQgdG8gU3BlZWNoIGZhaWxlZCIsICJ0ZXh0VG9TcGVlY2giKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUucGxheUF1ZGlvID0gZnVuY3Rpb24odXJsLCBvcHRpb25zKSB7CiAgICAgIGlmIChvcHRpb25zICE9IG51bGwpIHsKICAgICAgICBvcHRpb25zWyJsb29wIl0gPSB0aGlzLmF1ZGlvUHJvcGVydGllc1sibG9vcCJdOwogICAgICAgIG9wdGlvbnNbImNvbnRyb2xzIl0gPSB0aGlzLmF1ZGlvUHJvcGVydGllc1siY29udHJvbHMiXTsKICAgICAgfQogICAgICByZXR1cm4gTU1KUy5zcGVlY2hraXQucGxheUF1ZGlvKHVybCwgdGhpcy5hdWRpb1Byb3BlcnRpZXMsIGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgaWYgKHJlc3BvbnNlWydyZXN1bHQnXSA8IDEpIHsKICAgICAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoInZvaWNlRXJyb3IiLCAiUGxheWluZyBhdWRpbyBmYWlsZWQiLCAicGxheUF1ZGlvIik7CiAgICAgICAgfQogICAgICB9KTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLnN0b3BBdWRpbyA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gTU1KUy5zcGVlY2hraXQuc3RvcEF1ZGlvKGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgaWYgKHJlc3BvbnNlWydyZXN1bHQnXSA8IDEpIHsKICAgICAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoInZvaWNlRXJyb3IiLCAiU3RvcCBwbGF5aW5nIGF1ZGlvIGZhaWxlZCIsICJzdG9wQXVkaW8iKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUuY2FjaGVBdWRpbyA9IGZ1bmN0aW9uKHVybCkgewogICAgICByZXR1cm4gTU1KUy5zcGVlY2hraXQuY2FjaGVBdWRpbyh1cmwsIGZ1bmN0aW9uKHJlc3BvbnNlKSB7CiAgICAgICAgaWYgKHJlc3BvbnNlWydyZXN1bHQnXSA8IDEpIHsKICAgICAgICAgIHJldHVybiBNTUpTLmxpc3RlbmVyTWFuYWdlci5maXJlRXZlbnRDYWxsYmFja3MoInZvaWNlRXJyb3IiLCAiQXVkaW8gY2FjaGluZyBmYWlsZWQiLCAiY2FjaGVBdWRpbyIpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5zYW1wbGVCYWNrZ3JvdW5kQXVkaW9MZXZlbCA9IGZ1bmN0aW9uKCkgewogICAgICByZXR1cm4gTU1KUy5zcGVlY2hraXQuc2FtcGxlQmFja2dyb3VuZEF1ZGlvTGV2ZWwoZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICBpZiAocmVzcG9uc2VbJ3Jlc3VsdCddIDwgMSkgewogICAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygidm9pY2VFcnJvciIsICJTYW1wbGluZyBvZiBiYWNrZ3JvdW5kIGF1ZGlvIGZhaWxlZCIsICJzYW1wbGVCYWNrZ3JvdW5kQXVkaW9MZXZlbCIpOwogICAgICAgIH0KICAgICAgfSk7CiAgICB9OwoKICAgIE1SQUlELnByb3RvdHlwZS5yZWxlYXNlVm9pY2UgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMuc3BlZWNoa2l0LnJlbGVhc2VWb2ljZShmdW5jdGlvbigpIHt9KTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmFkZEN1c3RvbVZvaWNlV29yZHMgPSBmdW5jdGlvbih3b3JkcykgewogICAgICByZXR1cm4gTU1KUy5zcGVlY2hraXQuYWRkQ3VzdG9tVm9pY2VXb3Jkcyh3b3JkcywgZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICBpZiAocmVzcG9uc2VbJ3Jlc3VsdCddIDwgMSkgewogICAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygidm9pY2VFcnJvciIsICJBZGRpbmcgY3VzdG9tIHdvcmRzIGZhaWxlZCIsICJhZGRDdXN0b21Wb2ljZVdvcmRzIik7CiAgICAgICAgfQogICAgICB9KTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmRlbGV0ZUN1c3RvbVZvaWNlV29yZHMgPSBmdW5jdGlvbih3b3JkcykgewogICAgICByZXR1cm4gTU1KUy5zcGVlY2hraXQuZGVsZXRlQ3VzdG9tVm9pY2VXb3Jkcyh3b3JkcywgZnVuY3Rpb24ocmVzcG9uc2UpIHsKICAgICAgICBpZiAocmVzcG9uc2VbJ3Jlc3VsdCddIDwgMSkgewogICAgICAgICAgcmV0dXJuIE1NSlMubGlzdGVuZXJNYW5hZ2VyLmZpcmVFdmVudENhbGxiYWNrcygidm9pY2VFcnJvciIsICJEZWxldGluZyBjdXN0b20gd29yZHMgZmFpbGVkIiwgImRlbGV0ZUN1c3RvbVZvaWNlV29yZHMiKTsKICAgICAgICB9CiAgICAgIH0pOwogICAgfTsKCiAgICBNUkFJRC5wcm90b3R5cGUuZ2V0UmVjb2duaXRpb25SZXN1bHRzID0gZnVuY3Rpb24oKSB7CiAgICAgIHJldHVybiBNTUpTLnNwZWVjaGtpdC5nZXRSZWNvZ25pdGlvblJlc3VsdHMoKTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmdldEF1ZGlvTGV2ZWwgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMuc3BlZWNoa2l0LmdldEF1ZGlvTGV2ZWwoKTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmdldFZvaWNlU3RhdGUgPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMuc3BlZWNoa2l0LmdldFZvaWNlU3RhdGUoKTsKICAgIH07CgogICAgTVJBSUQucHJvdG90eXBlLmdldEF1ZGlvUG9zaXRpb24gPSBmdW5jdGlvbigpIHsKICAgICAgcmV0dXJuIE1NSlMuc3BlZWNoa2l0LmdldEF1ZGlvUG9zaXRpb24oKTsKICAgIH07CgogICAgcmV0dXJuIE1SQUlEOwoKICB9KShNTUJyaWRnZU9iamVjdCk7CiAgKGZ1bmN0aW9uKCkgewogICAgaWYgKHR5cGVvZiBNTUpTLnNkayA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTUpTLnNkayA9IG5ldyBNTVNES0ludGVyZmFjZTsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1KUy5kZXZpY2UgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1KUy5kZXZpY2UgPSBuZXcgTU1EZXZpY2U7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NSlMubWVkaWEgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1KUy5tZWRpYSA9IG5ldyBNTU1lZGlhOwogICAgfQogICAgaWYgKHR5cGVvZiBNTUpTLmZpbGVNYW5hZ2VyID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NSlMuZmlsZU1hbmFnZXIgPSBuZXcgTU1GaWxlTWFuYWdlcjsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1KUy5ub3RpZmljYXRpb24gPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1KUy5ub3RpZmljYXRpb24gPSBuZXcgTU1Ob3RpZmljYXRpb247CiAgICB9CiAgICBpZiAodHlwZW9mIE1NSlMuaW50ZXJzdGl0aWFsID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NSlMuaW50ZXJzdGl0aWFsID0gbmV3IE1NSW50ZXJzdGl0aWFsOwogICAgfQogICAgaWYgKHR5cGVvZiBNTUpTLmNhY2hlZFZpZGVvID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NSlMuY2FjaGVkVmlkZW8gPSBuZXcgTU1DYWNoZWRWaWRlbzsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1KUy5icmFuZCA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTUpTLmJyYW5kID0gbmV3IE1NQnJhbmQ7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NSlMuaW5saW5lVmlkZW8gPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1KUy5pbmxpbmVWaWRlbyA9IG5ldyBNTUlubGluZVZpZGVvOwogICAgfQogICAgaWYgKHR5cGVvZiBNTUpTLnNvY2lhbCA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTUpTLnNvY2lhbCA9IG5ldyBNTVNvY2lhbDsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1KUy5wYXNzYm9vayA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTUpTLnBhc3Nib29rID0gbmV3IE1NUGFzc2Jvb2s7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NSlMuY2FsZW5kYXIgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1KUy5jYWxlbmRhciA9IG5ldyBNTUNhbGVuZGFyOwogICAgfQogICAgaWYgKHR5cGVvZiBNTUpTLmJhbm5lciA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTUpTLmJhbm5lciA9IG5ldyBNTUJhbm5lcjsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1KUy5hcHBzdG9yZSA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTUpTLmFwcHN0b3JlID0gbmV3IE1NQXBwU3RvcmU7CiAgICB9CiAgICBNTUpTLmFwcFN0b3JlID0gTU1KUy5hcHBzdG9yZTsKICAgIGlmICh0eXBlb2YgTU1KUy5wYXN0ZWJvYXJkID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NSlMucGFzdGVib2FyZCA9IG5ldyBNTVBhc3RlYm9hcmQ7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NSlMubGlzdGVuZXJNYW5hZ2VyID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NSlMubGlzdGVuZXJNYW5hZ2VyID0gbmV3IE1NTGlzdGVuZXJNYW5hZ2VyOwogICAgfQogICAgaWYgKHR5cGVvZiBNTUpTLnNwZWVjaGtpdCA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTUpTLnNwZWVjaGtpdCA9IG5ldyBNTVNwZWVjaGtpdDsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1KUy5taWNyb3Bob25lID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NSlMubWljcm9waG9uZSA9IG5ldyBNTU1pY3JvcGhvbmU7CiAgICB9CiAgICBpZiAodHlwZW9mIHdpbmRvdy5NTVNESyA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICB3aW5kb3cuTU1TREsgPSBNTUpTOwogICAgfQogICAgaWYgKHR5cGVvZiBNTVNESy5zZGsgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1TREsuc2RrID0gTU1KUy5zZGs7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NU0RLLmRldmljZSA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5kZXZpY2UgPSBNTUpTLmRldmljZTsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1TREsubWVkaWEgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1TREsubWVkaWEgPSBNTUpTLm1lZGlhOwogICAgfQogICAgaWYgKHR5cGVvZiBNTVNESy5maWxlTWFuYWdlciA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5maWxlTWFuYWdlciA9IE1NSlMuZmlsZU1hbmFnZXI7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NU0RLLm5vdGlmaWNhdGlvbiA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5ub3RpZmljYXRpb24gPSBNTUpTLm5vdGlmaWNhdGlvbjsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1TREsuaW50ZXJzdGl0aWFsID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NU0RLLmludGVyc3RpdGlhbCA9IE1NSlMuaW50ZXJzdGl0aWFsOwogICAgfQogICAgaWYgKHR5cGVvZiBNTUpTLmNhY2hlZFZpZGVvID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NU0RLLmNhY2hlZFZpZGVvID0gTU1KUy5jYWNoZWRWaWRlbzsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1TREsuYnJhbmQgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1TREsuYnJhbmQgPSBNTUpTLmJyYW5kOwogICAgfQogICAgaWYgKHR5cGVvZiBNTVNESy5pbmxpbmVWaWRlbyA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5pbmxpbmVWaWRlbyA9IE1NSlMuaW5saW5lVmlkZW87CiAgICB9CiAgICBpZiAodHlwZW9mIE1NU0RLLnNvY2lhbCA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5zb2NpYWwgPSBNTUpTLnNvY2lhbDsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1TREsucGFzc2Jvb2sgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1TREsucGFzc2Jvb2sgPSBNTUpTLnBhc3Nib29rOwogICAgfQogICAgaWYgKHR5cGVvZiBNTVNESy5jYWxlbmRhciA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5jYWxlbmRhciA9IE1NSlMuY2FsZW5kYXI7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NU0RLLmJhbm5lciA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5iYW5uZXIgPSBNTUpTLmJhbm5lcjsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1TREsuYXBwc3RvcmUgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgTU1TREsuYXBwc3RvcmUgPSBNTUpTLmFwcHN0b3JlOwogICAgfQogICAgTU1TREsuYXBwU3RvcmUgPSBNTUpTLmFwcHN0b3JlOwogICAgaWYgKHR5cGVvZiBNTVNESy5wYXN0ZWJvYXJkID09PSBNTUpTLlRZUEVfVU5ERUZJTkVEKSB7CiAgICAgIE1NU0RLLnBhc3RlYm9hcmQgPSBNTUpTLnBhc3RlYm9hcmQ7CiAgICB9CiAgICBpZiAodHlwZW9mIE1NU0RLLnNwZWVjaGtpdCA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5zcGVlY2hraXQgPSBNTUpTLnNwZWVjaGtpdDsKICAgIH0KICAgIGlmICh0eXBlb2YgTU1TREsubWljcm9waG9uZSA9PT0gTU1KUy5UWVBFX1VOREVGSU5FRCkgewogICAgICBNTVNESy5taWNyb3Bob25lID0gTU1KUy5taWNyb3Bob25lOwogICAgfQogICAgaWYgKHR5cGVvZiB3aW5kb3cubXJhaWQgPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgd2luZG93Lm1yYWlkID0gbmV3IE1SQUlEOwogICAgfQogICAgaWYgKHR5cGVvZiB3aW5kb3cuTU0gPT09IE1NSlMuVFlQRV9VTkRFRklORUQpIHsKICAgICAgcmV0dXJuIHdpbmRvdy5NTSA9IE1NSlM7CiAgICB9CiAgfSkoKTsKICBNTUpTLnV0aWxzLmxpc3RlbkZvckJyb3dzZXJSZWFkeSgoZnVuY3Rpb24oKSB7CiAgICB2YXIgdGltZXI7CgogICAgcmV0dXJuIHRpbWVyID0gc2V0SW50ZXJ2YWwoZnVuY3Rpb24oKSB7CiAgICAgIHZhciBjb21tYW5kLCBlOwoKICAgICAgaWYgKE1NSlMuc2RrLnN0YXRlICE9PSAibG9hZGluZyIpIHsKICAgICAgICBpZiAoTU1KUy5leGVjdXRpbmdDb21tYW5kID09PSBmYWxzZSAmJiBNTUpTLmNvbW1hbmRRdWV1ZS5sZW5ndGggPiAwICYmIE1NSlMuZXhlY3V0aW5nQ29tbWFuZERlbGF5ID09PSAwKSB7CiAgICAgICAgICBjb21tYW5kID0gTU1KUy5jb21tYW5kUXVldWUuc2hpZnQoKTsKICAgICAgICAgIE1NSlMudXRpbHMuY29uc29sZUxvZygicnVubmluZyBjb21tYW5kOiAiICsgY29tbWFuZC51cmwpOwogICAgICAgICAgdHJ5IHsKICAgICAgICAgICAgcmV0dXJuIGNvbW1hbmQucGVyZm9ybSgpOwogICAgICAgICAgfSBjYXRjaCAoX2Vycm9yKSB7CiAgICAgICAgICAgIGUgPSBfZXJyb3I7CiAgICAgICAgICAgIHJldHVybiBNTUpTLnV0aWxzLmNvbnNvbGVMb2coIkZhaWxlZCB0byBydW4gY29tbWFuZDogIiArIGUubWVzc2FnZWFsZXJ0KTsKICAgICAgICAgIH0KICAgICAgICB9CiAgICAgIH0KICAgIH0sIDEpOwogIH0pKCkpOwp9Cg==";
    static final String MRAID_JS_FILE_NAME = "mraid.js";
    private static final String MRAID_JS_REPLACE_HEAD_PATTERN = "<head>";
    static final String MRAID_JS_REPLACE_IDENTIFIER = "<script src=\"mraid.js\"></script>";
    private static final String MRAID_JS_REPLACE_PATTERN = "<script.*src=[\"|']mraid\\.js[\"|']";
    private static final String ORIGINAL_MMJS_URL = "http://lp.mydas.mobi/assets/mmjs/1.4/mm.js";
    static final String STATE_DEFAULT = "default";
    static final String STATE_EXPANDED = "expanded";
    static final String STATE_HIDDEN = "hidden";
    static final String STATE_LOADING = "loading";
    static WeakReference<Finished> finishedRef;

    interface Finished {
        void finished();
    }

    MRaid() {
    }

    static boolean isMRaidAd(String content) {
        if (content == null) {
            return false;
        }
        Pattern pattern = Pattern.compile(MRAID_JS_REPLACE_PATTERN);
        Matcher matcher = pattern.matcher(content);
        return matcher.find();
    }

    public static String injectMraidJs(Context context, String content) {
        Pattern pattern = Pattern.compile(MRAID_JS_REPLACE_PATTERN);
        Matcher matcher = pattern.matcher(content);
        String mraid = getMRaidJsPath(context);
        MMSDK.Log.d("Mraid path: " + getMRaidJsPath(context));
        if (matcher.find()) {
            content = matcher.replaceFirst("<script src=\"" + mraid + "\"");
        } else if (content.indexOf(MRAID_JS_REPLACE_HEAD_PATTERN) == -1) {
            content = "<script src=\"" + mraid + "\"></script>" + content;
        } else {
            Pattern pattern2 = Pattern.compile(MRAID_JS_REPLACE_HEAD_PATTERN);
            Matcher matcher2 = pattern2.matcher(content);
            if (matcher2.find()) {
                content = matcher2.replaceFirst("<head><script src=\"" + mraid + "\"></script>");
            }
        }
        if (content.indexOf("<html>") == -1) {
            return "<html><head></head><body style='margin:0;padding:0;'>" + content + "</body></html>";
        }
        return content;
    }

    static void setCallbackRef(Finished callback) {
        finishedRef = new WeakReference<>(callback);
    }

    public static void downloadMraidJs(final Context context, final String url) {
        if (!TextUtils.isEmpty(url)) {
            Utils.ThreadUtils.execute(new Runnable() {
                @Override
                public void run() {
                    Finished fin;
                    try {
                        try {
                            MMSDK.Log.w("MMJS -  download start (" + url + ")");
                            HttpGet httpGet = new HttpGet(url);
                            HttpResponse response = new DefaultHttpClient().execute(httpGet);
                            MMSDK.Log.w("MMJS -  download finish (" + url + ")");
                            if (MRaid.saveMRaid(context, response.getEntity().getContent())) {
                                if (MRaid.storeMraidUrl(context, url)) {
                                    MMSDK.Log.w("MMJS -  download saved (" + url + ")");
                                }
                                if (MRaid.finishedRef != null && (fin = MRaid.finishedRef.get()) != null) {
                                    fin.finished();
                                }
                            }
                        } catch (IllegalStateException e) {
                            e.printStackTrace();
                        }
                    } catch (MalformedURLException e2) {
                        e2.printStackTrace();
                    } catch (IOException e3) {
                        e3.printStackTrace();
                    }
                }
            });
        }
    }

    static boolean storeMraidUrl(Context context, String url) {
        if (TextUtils.isEmpty(url)) {
            return false;
        }
        SharedPreferences prefs = context.getSharedPreferences("MillennialMediaSettings", 0);
        SharedPreferences.Editor editor = prefs.edit();
        editor.putString(KEY_MMJS_URL, url);
        editor.commit();
        return true;
    }

    private static File getMRaidJsFile(Context context) {
        return new File(AdCache.getCacheDirectory(context), MRAID_JS_FILE_NAME);
    }

    static String getMRaidJsPath(Context context) {
        return Uri.fromFile(getMRaidJsFile(context)).toString();
    }

    static String getMMJSStats(Context context) {
        if (!hasMraidLocally(context)) {
            return "No MMJS Downloaded!";
        }
        File mmjs = getMRaidJsFile(context);
        BufferedReader reader = null;
        FileInputStream fileStream = null;
        String md5Hash = "";
        String buildDate = "";
        String version = "";
        try {
            FileInputStream fileStream2 = new FileInputStream(mmjs);
            try {
                byte[] contents = new byte[(int) mmjs.length()];
                fileStream2.read(contents);
                MessageDigest md = MessageDigest.getInstance("MD5");
                byte[] hashBytes = md.digest(contents);
                md5Hash = MMSDK.byteArrayToString(hashBytes);
                mmjs = getMRaidJsFile(context);
                BufferedReader reader2 = new BufferedReader(new FileReader(mmjs));
                for (int i = 0; i < 10; i++) {
                    try {
                        String line = reader2.readLine();
                        if (line == null) {
                            break;
                        }
                        if (!TextUtils.isEmpty(line)) {
                            if (line.contains("* Built") && TextUtils.isEmpty(buildDate)) {
                                buildDate = line;
                                MMSDK.Log.d("MMJS BuildDate:" + buildDate);
                            }
                            if (line.contains("* Version") && TextUtils.isEmpty(version)) {
                                version = line;
                                MMSDK.Log.d("MMJS Version:" + version);
                            }
                            if (!TextUtils.isEmpty(version) && !TextUtils.isEmpty(buildDate)) {
                                break;
                            }
                        }
                    } catch (Exception e) {
                        fileStream = fileStream2;
                        reader = reader2;
                        if (fileStream != null) {
                            try {
                                fileStream.close();
                            } catch (Exception e2) {
                            }
                        }
                        if (reader != null) {
                            reader.close();
                        }
                        Date date = new Date(mmjs.lastModified());
                        if (!TextUtils.isEmpty(version)) {
                        }
                    } catch (Throwable th) {
                        th = th;
                        fileStream = fileStream2;
                        reader = reader2;
                        if (fileStream != null) {
                            try {
                                fileStream.close();
                            } catch (Exception e3) {
                                throw th;
                            }
                        }
                        if (reader != null) {
                            reader.close();
                        }
                        throw th;
                    }
                }
                if (fileStream2 != null) {
                    try {
                        fileStream2.close();
                    } catch (Exception e4) {
                    }
                }
                if (reader2 != null) {
                    reader2.close();
                }
            } catch (Exception e5) {
                fileStream = fileStream2;
            } catch (Throwable th2) {
                th = th2;
                fileStream = fileStream2;
            }
        } catch (Exception e6) {
        } catch (Throwable th3) {
            th = th3;
        }
        Date date2 = new Date(mmjs.lastModified());
        if (!TextUtils.isEmpty(version)) {
            return String.format("MMJS Stats: buildDate[%s] MD5[%s] dlDate[%s] Size[%d] Url[%s]", buildDate, md5Hash, date2, Long.valueOf(mmjs.length()), getPreviousUrl(context));
        }
        return String.format("MMJS Stats: Version[%s] buildDate[%s] MD5[%s] dlDate[%s] Size[%d] Url[%s]", version, buildDate, md5Hash, date2, Long.valueOf(mmjs.length()), getPreviousUrl(context));
    }

    static boolean saveMRaid(Context context, InputStream is) {
        FileOutputStream out;
        File mraidJsFile = new File(AdCache.getCacheDirectory(context), MRAID_JS_FILE_NAME);
        MMSDK.Log.v("Saving mraid js to %s", mraidJsFile);
        FileOutputStream out2 = null;
        try {
            try {
                out = new FileOutputStream(mraidJsFile);
            } catch (Exception e) {
                e = e;
            }
        } catch (Throwable th) {
            th = th;
        }
        try {
            byte[] buf = new byte[1024];
            while (true) {
                int numread = is.read(buf);
                if (numread <= 0) {
                    break;
                }
                out.write(buf, 0, numread);
            }
            if (out != null) {
                try {
                    out.close();
                } catch (IOException e2) {
                    e2.printStackTrace();
                }
            }
            return true;
        } catch (Exception e3) {
            e = e3;
            out2 = out;
            if (mraidJsFile != null) {
                mraidJsFile.delete();
            }
            MMSDK.Log.e("Exception downloading component mraid.js: %s", e.getMessage());
            if (out2 != null) {
                try {
                    out2.close();
                } catch (IOException e4) {
                    e4.printStackTrace();
                }
            }
            return false;
        } catch (Throwable th2) {
            th = th2;
            out2 = out;
            if (out2 != null) {
                try {
                    out2.close();
                } catch (IOException e5) {
                    e5.printStackTrace();
                }
            }
            throw th;
        }
    }

    public static boolean isMRaidUpdated(Context context, String mmjsUrl) {
        boolean hasMraidLocally = hasMraidLocally(context);
        if (!hasMraidLocally && ORIGINAL_MMJS_URL.equals(mmjsUrl) && saveIncludedMMJS(context, mmjsUrl)) {
            MMSDK.Log.w("MMJS - Using bundled MMJS");
            return true;
        }
        String previousUrl = getPreviousUrl(context);
        boolean isSameUrl = !TextUtils.isEmpty(previousUrl) && previousUrl.equals(mmjsUrl);
        if (isSameUrl) {
            MMSDK.Log.w("MMJS - same URL");
        }
        return isSameUrl && hasMraidLocally;
    }

    static String getPreviousUrl(Context context) {
        SharedPreferences prefs = context.getSharedPreferences("MillennialMediaSettings", 0);
        String previousUrl = prefs.getString(KEY_MMJS_URL, "");
        return previousUrl;
    }

    public static boolean hasMraidLocally(Context context) {
        File mmjs = getMRaidJsFile(context);
        if (mmjs != null) {
            MMSDK.Log.d("@@-MMJS File location: " + mmjs.getAbsolutePath());
        }
        return mmjs != null && mmjs.exists();
    }

    static boolean saveIncludedMMJS(Context context, String mmjsUrl) {
        byte[] mmjsBytesFirst = Base64.decode(MMJS_1_4_PART1);
        byte[] mmjsBytesSecond = Base64.decode(MMJS_1_4_PART2);
        if (mmjsBytesFirst == null || mmjsBytesSecond == null) {
            return false;
        }
        byte[] mmjsComplete = new byte[mmjsBytesFirst.length + mmjsBytesSecond.length];
        System.arraycopy(mmjsBytesFirst, 0, mmjsComplete, 0, mmjsBytesFirst.length);
        System.arraycopy(mmjsBytesSecond, 0, mmjsComplete, mmjsBytesFirst.length, mmjsBytesSecond.length);
        ByteArrayInputStream byteStream = new ByteArrayInputStream(mmjsComplete);
        return saveMRaid(context, byteStream) && storeMraidUrl(context, mmjsUrl);
    }
}