Return-Path: Delivered-To: new-httpd-archive@hyperreal.org Received: (qmail 17973 invoked by uid 6000); 1 Aug 1999 14:50:07 -0000 Received: (qmail 17964 invoked from network); 1 Aug 1999 14:50:04 -0000 Received: from ns.skylink.it (root@194.177.113.1) by taz.hyperreal.org with SMTP; 1 Aug 1999 14:50:04 -0000 Received: from kim.ispra.webweaving.org (va-143.skylink.it [194.185.55.143]) by ns.skylink.it (8.9.1/8.8.8) with ESMTP id QAA31093; Sun, 1 Aug 1999 16:48:52 +0200 Received: from kim.ispra.webweaving.org (kim.ispra.webweaving.org [10.0.0.2]) by kim.ispra.webweaving.org (8.8.8/8.8.5) with ESMTP id OAA24417; Sun, 1 Aug 1999 14:48:56 GMT X-Passed: MX on Ispra.WebWeaving.org Sun, 1 Aug 1999 14:48:56 GMT and masked X-No-Spam: Neither the receipients nor the senders email address(s) are to be used for Unsolicited (Commercial) Email without the explicit written consent of either party; as a per-message fee is incurred for inbound and outbound traffic to the originator. Posted-Date: Sun, 1 Aug 1999 14:48:56 GMT Date: Sun, 1 Aug 1999 16:48:55 +0200 (CEST) From: Dirk-Willem van Gulik X-Sender: dirkx@kim.ispra.webweaving.org To: new-httpd@apache.org cc: Clinton Wong , "Life is hard, and then you die." Subject: Re: PATCH: ap_md5c.c understands SHA1 (Netscape web server) passwords In-Reply-To: Message-ID: MIME-Version: 1.0 Content-Type: MULTIPART/MIXED; BOUNDARY="0-1671077389-933518935=:16065" Sender: new-httpd-owner@apache.org Precedence: bulk Reply-To: new-httpd@apache.org Status: O This message is in MIME format. The first part should be readable text, while the remaining parts are likely unreadable without MIME-aware tools. Send mail to mime@docserver.cac.washington.edu for more info. --0-1671077389-933518935=:16065 Content-Type: TEXT/PLAIN; charset=US-ASCII Hmm, this was the patch I had in mind; looking at either implementation I do see not that much different. Though anyone is free to take this further and really abstract the md5, sha1 and the various encoding formats, i.e. base64, mime-like 64 and what else might be in use. What is done here to Clinton's files is the following; Move ap_validate_passwd() into a new ap_checkpass.c file. Split up ap_md5c.c into an md5 and an sha1 specific file Moved Clinton's perl support files to support/SHA1 Entry in CHANGES Entry in 1.3 feature doc's Any objections to commiting this? I am still testing it, but intend to be done with it today. Dw Index: htdocs/manual/new_features_1_3.html =================================================================== RCS file: /x3/home/cvs/apache-1.3/htdocs/manual/new_features_1_3.html,v retrieving revision 1.79 diff -u -r1.79 new_features_1_3.html --- new_features_1_3.html 1999/03/23 14:30:40 1.79 +++ new_features_1_3.html 1999/08/01 14:37:18 @@ -675,6 +675,15 @@ +
Support for Netscape style SHA1 encrypted passwords
+
To facilitate migration or integration of BasicAuth password + schemes where the password is encrypted using SHA1 (as opposed + to apache's build in MD5 and/or the OS specific crypt(3) function + ) passwords prefixed with with {SHA1} are taken + as Base64 encoded SHA1 passwords. More information and + some utilities to convert Netscape ldap/ldif entries can be + found in support/SHA1. + Index: src/CHANGES =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/CHANGES,v retrieving revision 1.1406 diff -u -r1.1406 CHANGES --- CHANGES 1999/07/31 03:30:16 1.1406 +++ CHANGES 1999/08/01 14:38:00 @@ -1,5 +1,12 @@ Changes with Apache 1.3.8 + *) Added SHA1 password encryption support to easy migration from + Netscape servers. See support/SHA1 for more information; based + on the code contributed by Clinton Wong . + Caused the separation of ap_md5.c into md5, sha1 and a general + ap_checkpass.c with just a validate_passwd routine. + [dirkx] + *) Change for EBCDIC platforms (TPF and BS2000) to correctly deal with ASCII/EBCDIC conversions in "ident" query. [David McCreedy ] Index: src/ap/Makefile.tmpl =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/ap/Makefile.tmpl,v retrieving revision 1.32 diff -u -r1.32 Makefile.tmpl --- Makefile.tmpl 1999/05/31 17:09:30 1.32 +++ Makefile.tmpl 1999/08/01 14:38:01 @@ -6,7 +6,7 @@ LIB=libap.a OBJS=ap_cpystrn.o ap_execve.o ap_fnmatch.o ap_getpass.o ap_md5c.o ap_signal.o \ - ap_slack.o ap_snprintf.o + ap_slack.o ap_snprintf.o ap_sha1.o ap_checkpass.o .c.o: $(CC) -c $(INCLUDES) $(CFLAGS) $< Index: src/ap/ap_md5c.c =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/ap/ap_md5c.c,v retrieving revision 1.27 diff -u -r1.27 ap_md5c.c --- ap_md5c.c 1999/04/27 20:36:28 1.27 +++ ap_md5c.c 1999/08/01 14:38:05 @@ -415,7 +415,7 @@ * Define the Magic String prefix that identifies a password as being * hashed using our algorithm. */ -static const char *apr1_id = "$apr1$"; +const char *apr1_id = "$apr1$"; /* * The following MD5 password encryption code was largely borrowed from @@ -586,41 +586,4 @@ memset(final, 0, sizeof(final)); ap_cpystrn(result, passwd, nbytes - 1); -} - -/* - * Validate a plaintext password against a smashed one. Use either - * crypt() (if available) or ap_MD5Encode(), depending upon the format - * of the smashed input password. Return NULL if they match, or - * an explanatory text string if they don't. - */ - -API_EXPORT(char *) ap_validate_password(const char *passwd, const char *hash) -{ - char sample[120]; - char *crypt_pw; - - if (!strncmp(hash, apr1_id, strlen(apr1_id))) { - /* - * The hash was created using our custom algorithm. - */ - ap_MD5Encode((const unsigned char *)passwd, - (const unsigned char *)hash, sample, sizeof(sample)); - } - else { - /* - * It's not our algorithm, so feed it to crypt() if possible. - */ -#if defined(WIN32) || defined(TPF) - /* - * On Windows, the only alternative to our MD5 algorithm is plain - * text. - */ - ap_cpystrn(sample, passwd, sizeof(sample) - 1); -#else - crypt_pw = crypt(passwd, hash); - ap_cpystrn(sample, crypt_pw, sizeof(sample) - 1); -#endif - } - return (strcmp(sample, hash) == 0) ? NULL : "password mismatch"; } Index: src/include/ap_md5.h =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/include/ap_md5.h,v retrieving revision 1.5 diff -u -r1.5 ap_md5.h --- ap_md5.h 1999/04/08 20:56:39 1.5 +++ ap_md5.h 1999/08/01 14:38:08 @@ -104,6 +104,8 @@ unsigned char buffer[64]; /* input buffer */ } AP_MD5_CTX; +const char *apr1_id; /* MD5 passwd marker string */ + API_EXPORT(void) ap_MD5Init(AP_MD5_CTX *context); API_EXPORT(void) ap_MD5Update(AP_MD5_CTX *context, const unsigned char *input, unsigned int inputLen); Index: src/modules/standard/mod_auth.c =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/modules/standard/mod_auth.c,v retrieving revision 1.45 diff -u -r1.45 mod_auth.c --- mod_auth.c 1999/02/03 16:22:32 1.45 +++ mod_auth.c 1999/08/01 14:38:10 @@ -74,7 +74,7 @@ #include "http_core.h" #include "http_log.h" #include "http_protocol.h" -#include "ap_md5.h" +#include "ap_checkpass.h" typedef struct auth_config_struct { char *auth_pwfile; Index: src/modules/standard/mod_auth_db.c =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/modules/standard/mod_auth_db.c,v retrieving revision 1.40 diff -u -r1.40 mod_auth_db.c --- mod_auth_db.c 1999/02/03 16:22:32 1.40 +++ mod_auth_db.c 1999/08/01 14:38:11 @@ -96,7 +96,7 @@ #include "http_log.h" #include "http_protocol.h" #include -#include "ap_md5.h" +#include "ap_checkpass.h" #if defined(DB_VERSION_MAJOR) && (DB_VERSION_MAJOR == 2) #define DB2 Index: src/modules/standard/mod_auth_dbm.c =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/modules/standard/mod_auth_dbm.c,v retrieving revision 1.46 diff -u -r1.46 mod_auth_dbm.c --- mod_auth_dbm.c 1999/06/09 11:13:55 1.46 +++ mod_auth_dbm.c 1999/08/01 14:38:14 @@ -80,7 +80,7 @@ #else #include #endif -#include "ap_md5.h" +#include "ap_checkpass.h" /* * Module definition information - the part between the -START and -END Index: src/support/README =================================================================== RCS file: /x3/home/cvs/apache-1.3/src/support/README,v retrieving revision 1.1 diff -u -r1.1 README --- README 1999/04/05 13:52:20 1.1 +++ README 1999/08/01 14:38:19 @@ -55,3 +55,8 @@ see the document `Apache suEXEC Support' under http://www.apache.org/docs/suexec.html . +SHA1 + This directory includes some utilities to allow Apache 1.3.6 to + recognize passwords in SHA1 format, as used by Netscape web + servers. It is not installed by default. + ? .AppleDouble --0-1671077389-933518935=:16065 Content-Type: TEXT/PLAIN; charset=US-ASCII; name="README.sha1" Content-Transfer-Encoding: BASE64 Content-ID: Content-Description: support/SHA1/README.sha1 Content-Disposition: attachment; filename="README.sha1" VGhpcyBkaXJlY3RvcnkgaW5jbHVkZXMgc29tZSB1dGlsaXRpZXMgdG8gYWxs b3cgQXBhY2hlIDEuMy42IHRvIA0KcmVjb2duaXplIHBhc3N3b3JkcyBpbiBT SEExIGZvcm1hdCwgYXMgdXNlZCBieSBOZXRzY2FwZSB3ZWIgc2VydmVycy4g IA0KDQpGcm9tIE5ldHNjYXBlJ3MgYWRtaW4gaW50ZXJmYWNlLCBleHBvcnQg dGhlIHBhc3N3b3JkIGRhdGFiYXNlIHRvIGFuIA0KbGRpZiBmaWxlIGFuZCB0 aGVuIHVzZSBjb252ZXJ0LnBsIGluIHRoaXMgZGlzdHJpYnV0aW9uIHRvIGdl bmVyYXRlIA0KYXBhY2hlIHN0eWxlIHBhc3N3b3JkIGZpbGVzLiAgDQoNCk5v dGU6IFNIQTEgc3VwcG9ydCBpcyB1c2VmdWwgZm9yIG1pZ3JhdGlvbiBwdXJw b3NlcywgYnV0IGlzIGxlc3MNCiAgICAgIHNlY3VyZSB0aGFuIEFwYWNoZSdz IHBhc3N3b3JkIGZvcm1hdCwgc2luY2UgQXBhY2hlJ3MgKE1ENSkNCiAgICAg IHBhc3N3b3JkIGZvcm1hdCB1c2VzIGEgcmFuZG9tIGVpZ2h0IGNoYXJhY3Rl ciBzYWx0IHRvIGdlbmVyYXRlDQogICAgICBvbmUgb2YgbWFueSBwb3NzaWJs ZSBoYXNoZXMgZm9yIHRoZSBzYW1lIHBhc3N3b3JkLiAgTmV0c2NhcGUNCiAg ICAgIHVzZXMgcGxhaW4gU0hBMSB3aXRob3V0IGEgc2FsdCwgc28gdGhlIHNh bWUgcGFzc3dvcmQNCiAgICAgIHdpbGwgYWx3YXlzIGdlbmVyYXRlIHRoZSBz YW1lIGhhc2gsIG1ha2luZyBpdCBlYXNpZXINCiAgICAgIHRvIGJyZWFrIHNp bmNlIHRoZSBzZWFyY2ggc3BhY2UgaXMgc21hbGxlci4NCg0KVGhpcyBjb2Rl IHdhcyBjb250cmlidXRlZCBieSBDbGludG9uIFdvbmcgPGNsaW50ZHdAbmV0 Y29tLmNvbT4uDQoNClJFQURNRS5zaGExIA0KCXRoaXMgZmlsZQ0KDQpjb252 ZXJ0LXNoYTEucGwgDQoJdGFrZXMgYW4gbGRpZiBkdW1wIGZyb20gTmV0c2Nh cGUncyB3ZWIgc2VydmVyIG9uDQogICAgICAgIHN0YW5kYXJkIGluLCBvdXRw dXRzIGFwYWNoZSBodHBhc3N3ZCBmb3JtYXQgb24gc3RhbmRhcmQgb3V0Lg0K DQogICAgICAgIFVzYWdlOiBjb252ZXJ0LnBsIDwgbGRpZiA+IHBhc3N3b3Jk cw0KDQpodHBhc3N3ZC1zaGExLnBsDQoJcGVybCBzY3JpcHQgdG8gZ2VuZXJh dGUgZW50cmllcyBpbiBhcGFjaGUgaHRwYXNzd2QgZm9ybWF0Lg0KDQogICAg ICAgCVVzYWdlOiBodHBhc3N3ZC1zaGExLnBsIHNvbWVfdXNlciBzb21lX3Bh c3N3b3JkDQoNCmxkaWYtc2hhMS5leGFtcGxlDQoJc2FtcGxlIGxkaWYgZHVt cCB3aXRoIG9uZSBzaGExIHBhc3N3b3JkIGFuZCBvbmUgY3J5cHQgcGFzc3dv cmQuDQoNCg== --0-1671077389-933518935=:16065 Content-Type: TEXT/PLAIN; charset=US-ASCII; name="convert-sha1.pl" Content-Transfer-Encoding: BASE64 Content-ID: Content-Description: support/SHA1/convert-sha1.pl Content-Disposition: attachment; filename="convert-sha1.pl" IyEvdXNyL2Jpbi9wZXJsIC13DQp1c2Ugc3RyaWN0Ow0KDQojIFRoaXMgaXMg cHVibGljIGRvbWFpbiBjb2RlLiAgRG8gd2hhdGV2ZXIgeW91IHdhbnQgd2l0 aCBpdC4NCiMgSXQgd2FzIG9yaWdpbmFsbHkgaW5jbHVkZWQgaW4gQ2xpbnRv biBXb25nJ3MgQXBhY2hlIDEuMy42IFNIQTEvbGRpZg0KIyBwYXRjaCBkaXN0 cmlidXRpb24gYXMgc2FtcGxlIGNvZGUgZm9yIGNvbnZlcnRpbmcgYWNjb3Vu dHMgZnJvbQ0KIyBsZGlmIGZvcm1hdCAoYXMgdXNlZCBieSBOZXRzY2FwZSB3 ZWIgc2VydmVycykgdG8gQXBhY2hlIHBhc3N3b3JkIGZvcm1hdC4NCg0KbXkg JHVpZD0nJzsNCm15ICRwYXNzd2Q9Jyc7DQoNCndoaWxlIChteSAkbGluZSA9 IDw+KSB7DQogIGNob21wICRsaW5lOw0KICBpZiAoICRsaW5lID1+IC91aWQ6 XHMqKC4rKS8pIHsgJHVpZCA9ICQxIH0NCiAgaWYgKCAkbGluZSA9fiAvdXNl cnBhc3N3b3JkOlxzKihce1x3K1x9LispLykgew0KICAgICRwYXNzd2QgPSAk MTsNCiAgICAkcGFzc3dkID1+IHMvXlx7Y3J5cHRcfS8vaTsgICMgQXBhY2hl IHN0b3JlcyBjcnlwdCB3aXRob3V0IGEgbWFnaWMgc3RyaW5nDQogIH0NCg0K ICBpZiAobGVuZ3RoKCRsaW5lKT09MCkgew0KDQogICAgaWYgKGxlbmd0aCAk dWlkIGFuZCBsZW5ndGggJHBhc3N3ZCkgew0KICAgICAgcHJpbnQgJHVpZCwg JzonLCAkcGFzc3dkLCAiXG4iOw0KICAgIH0gIyBvdXRwdXQgaWYgd2UgaGF2 ZSBzb21ldGhpbmcgdG8gcHJpbnQNCg0KICAgICR1aWQgPSAnJzsNCiAgICAk cGFzc3dkID0gJyc7DQoNCiAgfSAjIGlmIG5ld2xpbmUNCn0gIyB3aGlsZSBz b21ldGhpbmcgdG8gcmVhZA0KDQojIGhhbmRsZSBsYXN0IGVudHJ5IGlmIHRo ZXJlIGlzbid0IGEgbmV3bGluZSBiZWZvcmUgRU9GDQogICAgaWYgKGxlbmd0 aCAkdWlkIGFuZCBsZW5ndGggJHBhc3N3ZCkgew0KICBwcmludCAkdWlkLCAn OicsICRwYXNzd2QsICJcbiI7DQp9DQoNCg== --0-1671077389-933518935=:16065 Content-Type: TEXT/PLAIN; charset=US-ASCII; name="htpasswd-sha1.pl" Content-Transfer-Encoding: BASE64 Content-ID: Content-Description: support/SHA/htpasswd-sha1.pl Content-Disposition: attachment; filename="htpasswd-sha1.pl" IyEvdXNyL2Jpbi9wZXJsIC13DQp1c2Ugc3RyaWN0Ow0KIw0KIyBVdGlsaXR5 IHdoaWNoIHRha2VzIGEgdXNlcm5hbWUgYW5kIHBhc3N3b3JkDQojIG9uIHRo ZSBjb21tYW5kIGxpbmUgYW5kIGdlbmVyYXRlcyBhIHVzZXJuYW1lDQojIHNo YTEtZW5jcnl0cGVkIHBhc3N3b3JkIG9uIHRoZSBzdGRvdXQuDQojIA0KIyBU eXBpY2FsIHVzZWFnZToNCiMgCS4vaHRwYXNzd2Qtc2hhMS5wbCBkaXJreCBN eVNlY3JldCA+PiBzaGExLXBhc3N3ZA0KIw0KIyBUaGlzIGlzIHB1YmxpYyBk b21haW4gY29kZS4gIERvIHdoYXRldmVyIHlvdSB3YW50IHdpdGggaXQuDQoj IEl0IHdhcyBvcmlnaW5hbGx5IGluY2x1ZGVkIGluIENsaW50b24gV29uZydz IEFwYWNoZSAxLjMuNiBTSEExL2xkaWYNCiMgcGF0Y2ggZGlzdHJpYnV0aW9u IGFzIHNhbXBsZSBjb2RlIGZvciBnZW5lcmF0aW5nIGVudHJpZXMgZm9yDQoj IEFwYWNoZSBwYXNzd29yZCBmaWxlcyB1c2luZyBTSEExLg0KDQp1c2UgTUlN RTo6QmFzZTY0OyAgIyBodHRwOi8vd3d3LmNwYW4ub3JnL21vZHVsZXMvYnkt bW9kdWxlL01JTUUvDQp1c2UgRGlnZXN0OjpTSEExOyAgIyBodHRwOi8vd3d3 LmNwYW4ub3JnL21vZHVsZXMvYnktbW9kdWxlL01ENS8NCg0KaWYgKCQjQVJH ViE9MSkgeyBkaWUgIlVzYWdlICQwOiB1c2VyIHBhc3N3b3JkXG4iIH0NCg0K cHJpbnQgJEFSR1ZbMF0sICc6e1NIQX0nLCBlbmNvZGVfYmFzZTY0KCBEaWdl c3Q6OlNIQTE6OnNoYTEoJEFSR1ZbMV0pICk7DQoNCg== --0-1671077389-933518935=:16065 Content-Type: TEXT/PLAIN; charset=US-ASCII; name="ap_checkpass.c" Content-Transfer-Encoding: BASE64 Content-ID: Content-Description: ap/ap_checkpass.c Content-Disposition: attachment; filename="ap_checkpass.c" LyogPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09 PT09PT09PT09PT09PT09PT09PT09PT09PT0NCiAqIENvcHlyaWdodCAoYykg MTk5Ni0xOTk5IFRoZSBBcGFjaGUgR3JvdXAuICBBbGwgcmlnaHRzIHJlc2Vy dmVkLg0KICoNCiAqIFJlZGlzdHJpYnV0aW9uIGFuZCB1c2UgaW4gc291cmNl IGFuZCBiaW5hcnkgZm9ybXMsIHdpdGggb3Igd2l0aG91dA0KICogbW9kaWZp Y2F0aW9uLCBhcmUgcGVybWl0dGVkIHByb3ZpZGVkIHRoYXQgdGhlIGZvbGxv d2luZyBjb25kaXRpb25zDQogKiBhcmUgbWV0Og0KICoNCiAqIDEuIFJlZGlz dHJpYnV0aW9ucyBvZiBzb3VyY2UgY29kZSBtdXN0IHJldGFpbiB0aGUgYWJv dmUgY29weXJpZ2h0DQogKiAgICBub3RpY2UsIHRoaXMgbGlzdCBvZiBjb25k aXRpb25zIGFuZCB0aGUgZm9sbG93aW5nIGRpc2NsYWltZXIuIA0KICoNCiAq IDIuIFJlZGlzdHJpYnV0aW9ucyBpbiBiaW5hcnkgZm9ybSBtdXN0IHJlcHJv ZHVjZSB0aGUgYWJvdmUgY29weXJpZ2h0DQogKiAgICBub3RpY2UsIHRoaXMg bGlzdCBvZiBjb25kaXRpb25zIGFuZCB0aGUgZm9sbG93aW5nIGRpc2NsYWlt ZXIgaW4NCiAqICAgIHRoZSBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBt YXRlcmlhbHMgcHJvdmlkZWQgd2l0aCB0aGUNCiAqICAgIGRpc3RyaWJ1dGlv bi4NCiAqDQogKiAzLiBBbGwgYWR2ZXJ0aXNpbmcgbWF0ZXJpYWxzIG1lbnRp b25pbmcgZmVhdHVyZXMgb3IgdXNlIG9mIHRoaXMNCiAqICAgIHNvZnR3YXJl IG11c3QgZGlzcGxheSB0aGUgZm9sbG93aW5nIGFja25vd2xlZGdtZW50Og0K ICogICAgIlRoaXMgcHJvZHVjdCBpbmNsdWRlcyBzb2Z0d2FyZSBkZXZlbG9w ZWQgYnkgdGhlIEFwYWNoZSBHcm91cA0KICogICAgZm9yIHVzZSBpbiB0aGUg QXBhY2hlIEhUVFAgc2VydmVyIHByb2plY3QgKGh0dHA6Ly93d3cuYXBhY2hl Lm9yZy8pLiINCiAqDQogKiA0LiBUaGUgbmFtZXMgIkFwYWNoZSBTZXJ2ZXIi IGFuZCAiQXBhY2hlIEdyb3VwIiBtdXN0IG5vdCBiZSB1c2VkIHRvDQogKiAg ICBlbmRvcnNlIG9yIHByb21vdGUgcHJvZHVjdHMgZGVyaXZlZCBmcm9tIHRo aXMgc29mdHdhcmUgd2l0aG91dA0KICogICAgcHJpb3Igd3JpdHRlbiBwZXJt aXNzaW9uLiBGb3Igd3JpdHRlbiBwZXJtaXNzaW9uLCBwbGVhc2UgY29udGFj dA0KICogICAgYXBhY2hlQGFwYWNoZS5vcmcuDQogKg0KICogNS4gUHJvZHVj dHMgZGVyaXZlZCBmcm9tIHRoaXMgc29mdHdhcmUgbWF5IG5vdCBiZSBjYWxs ZWQgIkFwYWNoZSINCiAqICAgIG5vciBtYXkgIkFwYWNoZSIgYXBwZWFyIGlu IHRoZWlyIG5hbWVzIHdpdGhvdXQgcHJpb3Igd3JpdHRlbg0KICogICAgcGVy bWlzc2lvbiBvZiB0aGUgQXBhY2hlIEdyb3VwLg0KICoNCiAqIDYuIFJlZGlz dHJpYnV0aW9ucyBvZiBhbnkgZm9ybSB3aGF0c29ldmVyIG11c3QgcmV0YWlu IHRoZSBmb2xsb3dpbmcNCiAqICAgIGFja25vd2xlZGdtZW50Og0KICogICAg IlRoaXMgcHJvZHVjdCBpbmNsdWRlcyBzb2Z0d2FyZSBkZXZlbG9wZWQgYnkg dGhlIEFwYWNoZSBHcm91cA0KICogICAgZm9yIHVzZSBpbiB0aGUgQXBhY2hl IEhUVFAgc2VydmVyIHByb2plY3QgKGh0dHA6Ly93d3cuYXBhY2hlLm9yZy8p LiINCiAqDQogKiBUSElTIFNPRlRXQVJFIElTIFBST1ZJREVEIEJZIFRIRSBB UEFDSEUgR1JPVVAgYGBBUyBJUycnIEFORCBBTlkNCiAqIEVYUFJFU1NFRCBP UiBJTVBMSUVEIFdBUlJBTlRJRVMsIElOQ0xVRElORywgQlVUIE5PVCBMSU1J VEVEIFRPLCBUSEUNCiAqIElNUExJRUQgV0FSUkFOVElFUyBPRiBNRVJDSEFO VEFCSUxJVFkgQU5EIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUg0KICogUFVS UE9TRSBBUkUgRElTQ0xBSU1FRC4gIElOIE5PIEVWRU5UIFNIQUxMIFRIRSBB UEFDSEUgR1JPVVAgT1INCiAqIElUUyBDT05UUklCVVRPUlMgQkUgTElBQkxF IEZPUiBBTlkgRElSRUNULCBJTkRJUkVDVCwgSU5DSURFTlRBTCwNCiAqIFNQ RUNJQUwsIEVYRU1QTEFSWSwgT1IgQ09OU0VRVUVOVElBTCBEQU1BR0VTIChJ TkNMVURJTkcsIEJVVA0KICogTk9UIExJTUlURUQgVE8sIFBST0NVUkVNRU5U IE9GIFNVQlNUSVRVVEUgR09PRFMgT1IgU0VSVklDRVM7DQogKiBMT1NTIE9G IFVTRSwgREFUQSwgT1IgUFJPRklUUzsgT1IgQlVTSU5FU1MgSU5URVJSVVBU SU9OKQ0KICogSE9XRVZFUiBDQVVTRUQgQU5EIE9OIEFOWSBUSEVPUlkgT0Yg TElBQklMSVRZLCBXSEVUSEVSIElOIENPTlRSQUNULA0KICogU1RSSUNUIExJ QUJJTElUWSwgT1IgVE9SVCAoSU5DTFVESU5HIE5FR0xJR0VOQ0UgT1IgT1RI RVJXSVNFKQ0KICogQVJJU0lORyBJTiBBTlkgV0FZIE9VVCBPRiBUSEUgVVNF IE9GIFRISVMgU09GVFdBUkUsIEVWRU4gSUYgQURWSVNFRA0KICogT0YgVEhF IFBPU1NJQklMSVRZIE9GIFNVQ0ggREFNQUdFLg0KICogPT09PT09PT09PT09 PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09 PT09PT09PT09PT0NCiAqDQogKiBUaGlzIHNvZnR3YXJlIGNvbnNpc3RzIG9m IHZvbHVudGFyeSBjb250cmlidXRpb25zIG1hZGUgYnkgbWFueQ0KICogaW5k aXZpZHVhbHMgb24gYmVoYWxmIG9mIHRoZSBBcGFjaGUgR3JvdXAgYW5kIHdh cyBvcmlnaW5hbGx5IGJhc2VkDQogKiBvbiBwdWJsaWMgZG9tYWluIHNvZnR3 YXJlIHdyaXR0ZW4gYXQgdGhlIE5hdGlvbmFsIENlbnRlciBmb3INCiAqIFN1 cGVyY29tcHV0aW5nIEFwcGxpY2F0aW9ucywgVW5pdmVyc2l0eSBvZiBJbGxp bm9pcywgVXJiYW5hLUNoYW1wYWlnbi4NCiAqIEZvciBtb3JlIGluZm9ybWF0 aW9uIG9uIHRoZSBBcGFjaGUgR3JvdXAgYW5kIHRoZSBBcGFjaGUgSFRUUCBz ZXJ2ZXINCiAqIHByb2plY3QsIHBsZWFzZSBzZWUgPGh0dHA6Ly93d3cuYXBh Y2hlLm9yZy8+Lg0KICoNCiAqIFNpbXBsZSBwYXNzd29yZCB2ZXJpZnksIHdo aWNoICdrbm93J3MgYWJvdXQgdmFyaW91cyBwYXNzd29yZA0KICogdHlwZXMs IHN1Y2ggYXMgdGhlIHNpbXBsZSBiYXNlNjQgZW5jb2RlZCBjcnlwdCgpcywg TUQ1ICQgbWFya2VkDQogKiBGcmVlQlNEIHN0eWxlIGFuZCBuZXRzY2FwZSBT SEExJ3MuDQogKi8NCiNpbmNsdWRlIDxzdHJpbmcuaD4NCg0KI2luY2x1ZGUg ImFwX2NvbmZpZy5oIg0KI2luY2x1ZGUgImFwX21kNS5oIg0KI2luY2x1ZGUg ImFwX3NoYTEuaCINCiNpbmNsdWRlICJhcC5oIg0KI2lmZGVmIENIQVJTRVRf RUJDRElDDQojaW5jbHVkZSAiZWJjZGljLmgiDQojZW5kaWYgLypDSEFSU0VU X0VCQ0RJQyovDQojaWYgSEFWRV9DUllQVF9IDQojaW5jbHVkZSA8Y3J5cHQu aD4NCiNlbmRpZg0KDQovKg0KICogVmFsaWRhdGUgYSBwbGFpbnRleHQgcGFz c3dvcmQgYWdhaW5zdCBhIHNtYXNoZWQgb25lLiAgVXNlIGVpdGhlcg0KICog Y3J5cHQoKSAoaWYgYXZhaWxhYmxlKSwgYXBfTUQ1RW5jb2RlKCkgb3IgYXBf U0hBMUVuY29kZSBkZXBlbmRpbmcgDQogKiB1cG9uIHRoZSBmb3JtYXQgb2Yg dGhlIHNtYXNoZWQgaW5wdXQgcGFzc3dvcmQuICANCiAqDQogKiBSZXR1cm4g TlVMTCBpZiB0aGV5IG1hdGNoLCBvciBhbiBleHBsYW5hdG9yeSB0ZXh0IHN0 cmluZyBpZiB0aGV5IGRvbid0Lg0KICovDQoNCkFQSV9FWFBPUlQoY2hhciAq KSBhcF92YWxpZGF0ZV9wYXNzd29yZChjb25zdCBjaGFyICpwYXNzd2QsIGNv bnN0IGNoYXIgKmhhc2gpDQp7DQogICAgY2hhciBzYW1wbGVbMTIwXTsNCiAg ICBjaGFyICpjcnlwdF9wdzsNCg0KICAgIC8qIEZyZWVCU0Qgc3R5bGUgTUQ1 IHN0cmluZyANCiAgICAgKi8NCiAgICBpZiAoIXN0cm5jbXAoaGFzaCwgYXBy MV9pZCwgc3RybGVuKGFwcjFfaWQpKSkgew0KCS8qDQoJICogVGhlIGhhc2gg d2FzIGNyZWF0ZWQgdXNpbmcgb3VyIGN1c3RvbSBhbGdvcml0aG0uDQoJICov DQoJYXBfTUQ1RW5jb2RlKChjb25zdCB1bnNpZ25lZCBjaGFyICopcGFzc3dk LA0KCQkgICAgIChjb25zdCB1bnNpZ25lZCBjaGFyICopaGFzaCwgc2FtcGxl LCBzaXplb2Yoc2FtcGxlKSk7DQogICAgfQ0KICAgIC8qIE5ldHNjYXBlIC8g U0hBMSBsZGFwIHN0eWxlIHN0cm5nICANCiAgICAgKi8NCiAgICBlbHNlIGlm ICghc3RybmNtcChoYXNoLCBzaGExX2lkLCBzdHJsZW4oc2hhMV9pZCkpKSB7 DQoJLyogc2tpcCBTSEExIG1ha2VyDQoJaGFzaCArPSBzdHJsZW4oc2hhMV9p ZCk7DQogCWFwX3NoYTFfYmFzZTY0KHBhc3N3ZCwgc3RybGVuKHBhc3N3ZCks IHNhbXBsZSk7DQogICAgfQ0KICAgIGVsc2Ugew0KCS8qDQoJICogSXQncyBu b3Qgb3VyIGFsZ29yaXRobSwgc28gZmVlZCBpdCB0byBjcnlwdCgpIGlmIHBv c3NpYmxlLg0KCSAqLw0KI2lmIGRlZmluZWQoV0lOMzIpIHx8IGRlZmluZWQo VFBGKQ0KCS8qDQoJICogT24gV2luZG93cywgdGhlIG9ubHkgYWx0ZXJuYXRp dmUgdG8gb3VyIE1ENSBhbGdvcml0aG0gaXMgcGxhaW4NCgkgKiB0ZXh0Lg0K CSAqLw0KCWFwX2NweXN0cm4oc2FtcGxlLCBwYXNzd2QsIHNpemVvZihzYW1w bGUpIC0gMSk7DQojZWxzZQ0KCWNyeXB0X3B3ID0gY3J5cHQocGFzc3dkLCBo YXNoKTsNCglhcF9jcHlzdHJuKHNhbXBsZSwgY3J5cHRfcHcsIHNpemVvZihz YW1wbGUpIC0gMSk7DQojZW5kaWYNCiAgICB9DQogICAgcmV0dXJuIChzdHJj bXAoc2FtcGxlLCBoYXNoKSA9PSAwKSA/IE5VTEwgOiAicGFzc3dvcmQgbWlz bWF0Y2giOw0KfQ0K --0-1671077389-933518935=:16065 Content-Type: TEXT/PLAIN; charset=US-ASCII; name="ap_sha1.c" Content-Transfer-Encoding: BASE64 Content-ID: Content-Description: ap/ap_sha1.c Content-Disposition: attachment; filename="ap_sha1.c" LyogPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09 PT09PT09PT09PT09PT09PT09PT09PT09PT0NCiAqIENvcHlyaWdodCAoYykg MTk5Ni0xOTk5IFRoZSBBcGFjaGUgR3JvdXAuICBBbGwgcmlnaHRzIHJlc2Vy dmVkLg0KICoNCiAqIFJlZGlzdHJpYnV0aW9uIGFuZCB1c2UgaW4gc291cmNl IGFuZCBiaW5hcnkgZm9ybXMsIHdpdGggb3Igd2l0aG91dA0KICogbW9kaWZp Y2F0aW9uLCBhcmUgcGVybWl0dGVkIHByb3ZpZGVkIHRoYXQgdGhlIGZvbGxv d2luZyBjb25kaXRpb25zDQogKiBhcmUgbWV0Og0KICoNCiAqIDEuIFJlZGlz dHJpYnV0aW9ucyBvZiBzb3VyY2UgY29kZSBtdXN0IHJldGFpbiB0aGUgYWJv dmUgY29weXJpZ2h0DQogKiAgICBub3RpY2UsIHRoaXMgbGlzdCBvZiBjb25k aXRpb25zIGFuZCB0aGUgZm9sbG93aW5nIGRpc2NsYWltZXIuIA0KICoNCiAq IDIuIFJlZGlzdHJpYnV0aW9ucyBpbiBiaW5hcnkgZm9ybSBtdXN0IHJlcHJv ZHVjZSB0aGUgYWJvdmUgY29weXJpZ2h0DQogKiAgICBub3RpY2UsIHRoaXMg bGlzdCBvZiBjb25kaXRpb25zIGFuZCB0aGUgZm9sbG93aW5nIGRpc2NsYWlt ZXIgaW4NCiAqICAgIHRoZSBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBt YXRlcmlhbHMgcHJvdmlkZWQgd2l0aCB0aGUNCiAqICAgIGRpc3RyaWJ1dGlv bi4NCiAqDQogKiAzLiBBbGwgYWR2ZXJ0aXNpbmcgbWF0ZXJpYWxzIG1lbnRp b25pbmcgZmVhdHVyZXMgb3IgdXNlIG9mIHRoaXMNCiAqICAgIHNvZnR3YXJl IG11c3QgZGlzcGxheSB0aGUgZm9sbG93aW5nIGFja25vd2xlZGdtZW50Og0K ICogICAgIlRoaXMgcHJvZHVjdCBpbmNsdWRlcyBzb2Z0d2FyZSBkZXZlbG9w ZWQgYnkgdGhlIEFwYWNoZSBHcm91cA0KICogICAgZm9yIHVzZSBpbiB0aGUg QXBhY2hlIEhUVFAgc2VydmVyIHByb2plY3QgKGh0dHA6Ly93d3cuYXBhY2hl Lm9yZy8pLiINCiAqDQogKiA0LiBUaGUgbmFtZXMgIkFwYWNoZSBTZXJ2ZXIi IGFuZCAiQXBhY2hlIEdyb3VwIiBtdXN0IG5vdCBiZSB1c2VkIHRvDQogKiAg ICBlbmRvcnNlIG9yIHByb21vdGUgcHJvZHVjdHMgZGVyaXZlZCBmcm9tIHRo aXMgc29mdHdhcmUgd2l0aG91dA0KICogICAgcHJpb3Igd3JpdHRlbiBwZXJt aXNzaW9uLiBGb3Igd3JpdHRlbiBwZXJtaXNzaW9uLCBwbGVhc2UgY29udGFj dA0KICogICAgYXBhY2hlQGFwYWNoZS5vcmcuDQogKg0KICogNS4gUHJvZHVj dHMgZGVyaXZlZCBmcm9tIHRoaXMgc29mdHdhcmUgbWF5IG5vdCBiZSBjYWxs ZWQgIkFwYWNoZSINCiAqICAgIG5vciBtYXkgIkFwYWNoZSIgYXBwZWFyIGlu IHRoZWlyIG5hbWVzIHdpdGhvdXQgcHJpb3Igd3JpdHRlbg0KICogICAgcGVy bWlzc2lvbiBvZiB0aGUgQXBhY2hlIEdyb3VwLg0KICoNCiAqIDYuIFJlZGlz dHJpYnV0aW9ucyBvZiBhbnkgZm9ybSB3aGF0c29ldmVyIG11c3QgcmV0YWlu IHRoZSBmb2xsb3dpbmcNCiAqICAgIGFja25vd2xlZGdtZW50Og0KICogICAg IlRoaXMgcHJvZHVjdCBpbmNsdWRlcyBzb2Z0d2FyZSBkZXZlbG9wZWQgYnkg dGhlIEFwYWNoZSBHcm91cA0KICogICAgZm9yIHVzZSBpbiB0aGUgQXBhY2hl IEhUVFAgc2VydmVyIHByb2plY3QgKGh0dHA6Ly93d3cuYXBhY2hlLm9yZy8p LiINCiAqDQogKiBUSElTIFNPRlRXQVJFIElTIFBST1ZJREVEIEJZIFRIRSBB UEFDSEUgR1JPVVAgYGBBUyBJUycnIEFORCBBTlkNCiAqIEVYUFJFU1NFRCBP UiBJTVBMSUVEIFdBUlJBTlRJRVMsIElOQ0xVRElORywgQlVUIE5PVCBMSU1J VEVEIFRPLCBUSEUNCiAqIElNUExJRUQgV0FSUkFOVElFUyBPRiBNRVJDSEFO VEFCSUxJVFkgQU5EIEZJVE5FU1MgRk9SIEEgUEFSVElDVUxBUg0KICogUFVS UE9TRSBBUkUgRElTQ0xBSU1FRC4gIElOIE5PIEVWRU5UIFNIQUxMIFRIRSBB UEFDSEUgR1JPVVAgT1INCiAqIElUUyBDT05UUklCVVRPUlMgQkUgTElBQkxF IEZPUiBBTlkgRElSRUNULCBJTkRJUkVDVCwgSU5DSURFTlRBTCwNCiAqIFNQ RUNJQUwsIEVYRU1QTEFSWSwgT1IgQ09OU0VRVUVOVElBTCBEQU1BR0VTIChJ TkNMVURJTkcsIEJVVA0KICogTk9UIExJTUlURUQgVE8sIFBST0NVUkVNRU5U IE9GIFNVQlNUSVRVVEUgR09PRFMgT1IgU0VSVklDRVM7DQogKiBMT1NTIE9G IFVTRSwgREFUQSwgT1IgUFJPRklUUzsgT1IgQlVTSU5FU1MgSU5URVJSVVBU SU9OKQ0KICogSE9XRVZFUiBDQVVTRUQgQU5EIE9OIEFOWSBUSEVPUlkgT0Yg TElBQklMSVRZLCBXSEVUSEVSIElOIENPTlRSQUNULA0KICogU1RSSUNUIExJ QUJJTElUWSwgT1IgVE9SVCAoSU5DTFVESU5HIE5FR0xJR0VOQ0UgT1IgT1RI RVJXSVNFKQ0KICogQVJJU0lORyBJTiBBTlkgV0FZIE9VVCBPRiBUSEUgVVNF IE9GIFRISVMgU09GVFdBUkUsIEVWRU4gSUYgQURWSVNFRA0KICogT0YgVEhF IFBPU1NJQklMSVRZIE9GIFNVQ0ggREFNQUdFLg0KICogPT09PT09PT09PT09 PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09 PT09PT09PT09PT0NCiAqDQogKiBUaGlzIHNvZnR3YXJlIGNvbnNpc3RzIG9m IHZvbHVudGFyeSBjb250cmlidXRpb25zIG1hZGUgYnkgbWFueQ0KICogaW5k aXZpZHVhbHMgb24gYmVoYWxmIG9mIHRoZSBBcGFjaGUgR3JvdXAgYW5kIHdh cyBvcmlnaW5hbGx5IGJhc2VkDQogKiBvbiBwdWJsaWMgZG9tYWluIHNvZnR3 YXJlIHdyaXR0ZW4gYXQgdGhlIE5hdGlvbmFsIENlbnRlciBmb3INCiAqIFN1 cGVyY29tcHV0aW5nIEFwcGxpY2F0aW9ucywgVW5pdmVyc2l0eSBvZiBJbGxp bm9pcywgVXJiYW5hLUNoYW1wYWlnbi4NCiAqIEZvciBtb3JlIGluZm9ybWF0 aW9uIG9uIHRoZSBBcGFjaGUgR3JvdXAgYW5kIHRoZSBBcGFjaGUgSFRUUCBz ZXJ2ZXINCiAqIHByb2plY3QsIHBsZWFzZSBzZWUgPGh0dHA6Ly93d3cuYXBh Y2hlLm9yZy8+Lg0KICoNCiAqIFRoZSBvbmx5IGV4cG9ydGVkIGZ1bmN0aW9u Og0KICoNCiAqIAkgYXBfc2hhMV9iYXNlNjQoY2hhciAqY2xlYXIsIGludCBs ZW4sIGNoYXIgKm91dCk7DQogKg0KICogcHJvdmlkZXMgYSBtZWFucyB0byBT SEExIGNyeXB0L2VuY29kZSBhIHBsYWludGV4dCBwYXNzd29yZCBpbg0KICog YSB3YXkgd2hpY2ggbWFrZXMgcGFzc3dvcmQgZmlsZXMgY29tcGF0aWJsZSB3 aXRoIHRob3NlIGNvbW1vbmx5DQogKiB1c2VkIGluIG5ldHNjYXBlIHdlYiBh bmQgbGRhcCBpbnN0YWxsYXRpb25zLiBJdCB3YXMgcHV0IHRvZ2V0aGVyDQog KiBieSBDbGludG9uIFdvbmcgPGNsaW50ZHdAbmV0Y29tLmNvbT4sIHdobyBh bHNvIG5vdGVzIHRoYXQ6DQogKg0KICogTm90ZTogU0hBMSBzdXBwb3J0IGlz IHVzZWZ1bCBmb3IgbWlncmF0aW9uIHB1cnBvc2VzLCBidXQgaXMgbGVzcw0K ICogICAgIHNlY3VyZSB0aGFuIEFwYWNoZSdzIHBhc3N3b3JkIGZvcm1hdCwg c2luY2UgQXBhY2hlJ3MgKE1ENSkNCiAqICAgICBwYXNzd29yZCBmb3JtYXQg dXNlcyBhIHJhbmRvbSBlaWdodCBjaGFyYWN0ZXIgc2FsdCB0byBnZW5lcmF0 ZQ0KICogICAgIG9uZSBvZiBtYW55IHBvc3NpYmxlIGhhc2hlcyBmb3IgdGhl IHNhbWUgcGFzc3dvcmQuICBOZXRzY2FwZQ0KICogICAgIHVzZXMgcGxhaW4g U0hBMSB3aXRob3V0IGEgc2FsdCwgc28gdGhlIHNhbWUgcGFzc3dvcmQNCiAq ICAgICB3aWxsIGFsd2F5cyBnZW5lcmF0ZSB0aGUgc2FtZSBoYXNoLCBtYWtp bmcgaXQgZWFzaWVyDQogKiAgICAgdG8gYnJlYWsgc2luY2UgdGhlIHNlYXJj aCBzcGFjZSBpcyBzbWFsbGVyLg0KICoNCiAqIFNlZSBhbHNvIHRoZSBkb2N1 bWVudGF0aW9uIGluIHN1cHBvcnQvU0hBMSBhcyB0byBoaW50cyBvbiBob3cg dG8gDQogKiBtaWdyYXRlIGFuIGV4aXN0aW5nIG5ldHNjYXBlIGluc3RhbGxh dGlvbiBhbmQgb3RoZXIgc3VwcGxpZWQgdXRpdGxpdGVzLg0KICoNCiAqIFRo aXMgc29mdHdhcmUgYWxzbyBtYWtlcyB1c2Ugb2YgdGhlIGZvbGxvd2luZyBj b21wb25lbnRzOiANCiAqDQogKiBOSVNUIFNlY3VyZSBIYXNoIEFsZ29yaXRo bQ0KICogIAloZWF2aWx5IG1vZGlmaWVkIGJ5IFV3ZSBIb2xsZXJiYWNoIHVo QGFsdW1uaS5jYWx0ZWNoIGVkdQ0KICoJZnJvbSBQZXRlciBDLiBHdXRtYW5u J3MgaW1wbGVtZW50YXRpb24gYXMgZm91bmQgaW4NCiAqCUFwcGxpZWQgQ3J5 cHRvZ3JhcGh5IGJ5IEJydWNlIFNjaG5laWVyDQogKglUaGlzIGNvZGUgaXMg aGVyZWJ5IHBsYWNlZCBpbiB0aGUgcHVibGljIGRvbWFpbg0KICoNCiAqIE1J TUUgQmFzZSA2NCBlbmNvZGluZyBiYXNlZCBvbiBzcmMvbWV0YW1haWwvY29k ZXMuYyBpbiBtZXRhbWFpbCwNCiAqCWF2YWlsYWJsZSBhdDogZnRwOi8vdGh1 bXBlci5iZWxsY29yZS5jb20vcHViL25zYi8NCiAqDQogKiBNZXRhbWFpbCdz IGNvcHlyaWdodCBpczoNCiAqIAlDb3B5cmlnaHQgKGMpIDE5OTEgQmVsbCBD b21tdW5pY2F0aW9ucyBSZXNlYXJjaCwgSW5jLiAoQmVsbGNvcmUpDQogKiAJ UGVybWlzc2lvbiB0byB1c2UsIGNvcHksIG1vZGlmeSwgYW5kIGRpc3RyaWJ1 dGUgdGhpcyBtYXRlcmlhbCANCiAqCWZvciBhbnkgcHVycG9zZSBhbmQgd2l0 aG91dCBmZWUgaXMgaGVyZWJ5IGdyYW50ZWQsIHByb3ZpZGVkIA0KICoJdGhh dCB0aGUgYWJvdmUgY29weXJpZ2h0IG5vdGljZSBhbmQgdGhpcyBwZXJtaXNz aW9uIG5vdGljZSANCiAqCWFwcGVhciBpbiBhbGwgY29waWVzLCBhbmQgdGhh dCB0aGUgbmFtZSBvZiBCZWxsY29yZSBub3QgYmUgDQogKgl1c2VkIGluIGFk dmVydGlzaW5nIG9yIHB1YmxpY2l0eSBwZXJ0YWluaW5nIHRvIHRoaXMgDQog KgltYXRlcmlhbCB3aXRob3V0IHRoZSBzcGVjaWZpYywgcHJpb3Igd3JpdHRl biBwZXJtaXNzaW9uIA0KICoJb2YgYW4gYXV0aG9yaXplZCByZXByZXNlbnRh dGl2ZSBvZiBCZWxsY29yZS4gIEJFTExDT1JFIA0KICoJTUFLRVMgTk8gUkVQ UkVTRU5UQVRJT05TIEFCT1VUIFRIRSBBQ0NVUkFDWSBPUiBTVUlUQUJJTElU WSANCiAqCU9GIFRISVMgTUFURVJJQUwgRk9SIEFOWSBQVVJQT1NFLiAgSVQg SVMgUFJPVklERUQgIkFTIElTIiwgDQogKglXSVRIT1VUIEFOWSBFWFBSRVNT IE9SIElNUExJRUQgV0FSUkFOVElFUy4NCiAqLw0KDQojaW5jbHVkZSA8c3Ry aW5nLmg+DQoNCiNpbmNsdWRlICJhcF9jb25maWcuaCINCiNpbmNsdWRlICJh cF9zaGExLmgiDQojaW5jbHVkZSAiYXAuaCINCiNpZmRlZiBDSEFSU0VUX0VC Q0RJQw0KI2luY2x1ZGUgImViY2RpYy5oIg0KI2VuZGlmIC8qQ0hBUlNFVF9F QkNESUMqLw0KDQovKiBhIGJpdCBmYXN0ZXIgJiBiaWdnZXIsIGlmIGRlZmlu ZWQgKi8NCiNkZWZpbmUgVU5ST0xMX0xPT1BTDQoNCi8qIE5JU1QncyBwcm9w b3NlZCBtb2RpZmljYXRpb24gdG8gU0hBLCA3LzExLzk0ICovDQojZGVmaW5l IFVTRV9NT0RJRklFRF9TSEENCg0KLyogU0hBIGYoKS1mdW5jdGlvbnMgKi8N CiNkZWZpbmUgZjEoeCx5LHopCSgoeCAmIHkpIHwgKH54ICYgeikpDQojZGVm aW5lIGYyKHgseSx6KQkoeCBeIHkgXiB6KQ0KI2RlZmluZSBmMyh4LHkseikJ KCh4ICYgeSkgfCAoeCAmIHopIHwgKHkgJiB6KSkNCiNkZWZpbmUgZjQoeCx5 LHopCSh4IF4geSBeIHopDQoNCi8qIFNIQSBjb25zdGFudHMgKi8NCiNkZWZp bmUgQ09OU1QxCQkweDVhODI3OTk5TA0KI2RlZmluZSBDT05TVDIJCTB4NmVk OWViYTFMDQojZGVmaW5lIENPTlNUMwkJMHg4ZjFiYmNkY0wNCiNkZWZpbmUg Q09OU1Q0CQkweGNhNjJjMWQ2TA0KDQovKiAzMi1iaXQgcm90YXRlICovDQoN CiNkZWZpbmUgUk9UMzIoeCxuKQkoKHggPDwgbikgfCAoeCA+PiAoMzIgLSBu KSkpDQoNCiNkZWZpbmUgRlVOQyhuLGkpCQkJCQkJXA0KICAgIHRlbXAgPSBS T1QzMihBLDUpICsgZiMjbihCLEMsRCkgKyBFICsgV1tpXSArIENPTlNUIyNu OwlcDQogICAgRSA9IEQ7IEQgPSBDOyBDID0gUk9UMzIoQiwzMCk7IEIgPSBB OyBBID0gdGVtcA0KDQp0eXBlZGVmIHVuc2lnbmVkIGNoYXIgQllURTsgICAg IC8qIGFuIDgtYml0IHF1YW50aXR5ICovDQp0eXBlZGVmIHVuc2lnbmVkIGxv bmcgTE9ORzsgICAgIC8qIGEgMzItYml0IHF1YW50aXR5ICovDQogDQojZGVm aW5lIFNIQV9CTE9DS1NJWkUgICAgICAgICAgIDY0DQojZGVmaW5lIFNIQV9E SUdFU1RTSVpFICAgICAgICAgIDIwDQogDQp0eXBlZGVmIHN0cnVjdCB7DQog ICBMT05HIGRpZ2VzdFs1XTsgICAgICAgICAgICAgLyogbWVzc2FnZSBkaWdl c3QgKi8NCiAgIExPTkcgY291bnRfbG8sIGNvdW50X2hpOyAgICAvKiA2NC1i aXQgYml0IGNvdW50ICovDQogICBMT05HIGRhdGFbMTZdOyAgICAgICAgICAg ICAgLyogU0hBIGRhdGEgYnVmZmVyICovDQogICBpbnQgbG9jYWw7ICAgICAg ICAgICAgICAgICAgLyogdW5wcm9jZXNzZWQgYW1vdW50IGluIGRhdGEgKi8N CiAgIH0gU0hBX0lORk87DQoNCnZvaWQgc2hhX2luaXQoU0hBX0lORk8gKik7 DQp2b2lkIHNoYV91cGRhdGUoU0hBX0lORk8gKiwgQllURSAqLCBpbnQpOw0K dm9pZCBzaGFfZmluYWwoU0hBX0lORk8gKik7DQp2b2lkIHNoYV9yYXdfc3dh cChTSEFfSU5GTyAqKTsNCnZvaWQgb3V0cHV0NjRjaHVuayh1bnNpZ25lZCBj aGFyLCB1bnNpZ25lZCBjaGFyLCB1bnNpZ25lZCBjaGFyLA0KICAgICAgICAg ICAgICAgICAgIGludCwgdW5zaWduZWQgY2hhciAqKik7DQp2b2lkIGVuY29k ZV9taW1lNjQodW5zaWduZWQgY2hhciAqLCB1bnNpZ25lZCBjaGFyICosIGlu dCk7DQp2b2lkIHNoYTFfYmFzZTY0KGNoYXIgKiwgaW50LCBjaGFyICopOw0K DQovKiB7U0hBfSBpcyB0aGUgcHJlZml4IHVzZWQgZm9yIGJhc2U2NCBlbmNv ZGVkIHNoYTEgaW4NCiAqIGxkYXAgZGF0YSBpbnRlcmNoYW5nZSBmb3JtYXQu DQogKi8NCmNvbnN0IGNoYXIgKnNoYTFfaWQgPSAie1NIQX0iOw0KDQovKiBk byBTSEEgdHJhbnNmb3JtYXRpb24gKi8NCnN0YXRpYyB2b2lkIHNoYV90cmFu c2Zvcm0oU0hBX0lORk8gKnNoYV9pbmZvKQ0Kew0KICAgIGludCBpOw0KICAg IExPTkcgdGVtcCwgQSwgQiwgQywgRCwgRSwgV1s4MF07DQoNCiAgICBmb3Ig KGkgPSAwOyBpIDwgMTY7ICsraSkgew0KCVdbaV0gPSBzaGFfaW5mby0+ZGF0 YVtpXTsNCiAgICB9DQogICAgZm9yIChpID0gMTY7IGkgPCA4MDsgKytpKSB7 DQoJV1tpXSA9IFdbaS0zXSBeIFdbaS04XSBeIFdbaS0xNF0gXiBXW2ktMTZd Ow0KI2lmZGVmIFVTRV9NT0RJRklFRF9TSEENCglXW2ldID0gUk9UMzIoV1tp XSwgMSk7DQojZW5kaWYgLyogVVNFX01PRElGSUVEX1NIQSAqLw0KICAgIH0N CiAgICBBID0gc2hhX2luZm8tPmRpZ2VzdFswXTsNCiAgICBCID0gc2hhX2lu Zm8tPmRpZ2VzdFsxXTsNCiAgICBDID0gc2hhX2luZm8tPmRpZ2VzdFsyXTsN CiAgICBEID0gc2hhX2luZm8tPmRpZ2VzdFszXTsNCiAgICBFID0gc2hhX2lu Zm8tPmRpZ2VzdFs0XTsNCiNpZmRlZiBVTlJPTExfTE9PUFMNCiAgICBGVU5D KDEsIDApOyAgRlVOQygxLCAxKTsgIEZVTkMoMSwgMik7ICBGVU5DKDEsIDMp OyAgRlVOQygxLCA0KTsNCiAgICBGVU5DKDEsIDUpOyAgRlVOQygxLCA2KTsg IEZVTkMoMSwgNyk7ICBGVU5DKDEsIDgpOyAgRlVOQygxLCA5KTsNCiAgICBG VU5DKDEsMTApOyAgRlVOQygxLDExKTsgIEZVTkMoMSwxMik7ICBGVU5DKDEs MTMpOyAgRlVOQygxLDE0KTsNCiAgICBGVU5DKDEsMTUpOyAgRlVOQygxLDE2 KTsgIEZVTkMoMSwxNyk7ICBGVU5DKDEsMTgpOyAgRlVOQygxLDE5KTsNCg0K ICAgIEZVTkMoMiwyMCk7ICBGVU5DKDIsMjEpOyAgRlVOQygyLDIyKTsgIEZV TkMoMiwyMyk7ICBGVU5DKDIsMjQpOw0KICAgIEZVTkMoMiwyNSk7ICBGVU5D KDIsMjYpOyAgRlVOQygyLDI3KTsgIEZVTkMoMiwyOCk7ICBGVU5DKDIsMjkp Ow0KICAgIEZVTkMoMiwzMCk7ICBGVU5DKDIsMzEpOyAgRlVOQygyLDMyKTsg IEZVTkMoMiwzMyk7ICBGVU5DKDIsMzQpOw0KICAgIEZVTkMoMiwzNSk7ICBG VU5DKDIsMzYpOyAgRlVOQygyLDM3KTsgIEZVTkMoMiwzOCk7ICBGVU5DKDIs MzkpOw0KDQogICAgRlVOQygzLDQwKTsgIEZVTkMoMyw0MSk7ICBGVU5DKDMs NDIpOyAgRlVOQygzLDQzKTsgIEZVTkMoMyw0NCk7DQogICAgRlVOQygzLDQ1 KTsgIEZVTkMoMyw0Nik7ICBGVU5DKDMsNDcpOyAgRlVOQygzLDQ4KTsgIEZV TkMoMyw0OSk7DQogICAgRlVOQygzLDUwKTsgIEZVTkMoMyw1MSk7ICBGVU5D KDMsNTIpOyAgRlVOQygzLDUzKTsgIEZVTkMoMyw1NCk7DQogICAgRlVOQygz LDU1KTsgIEZVTkMoMyw1Nik7ICBGVU5DKDMsNTcpOyAgRlVOQygzLDU4KTsg IEZVTkMoMyw1OSk7DQoNCiAgICBGVU5DKDQsNjApOyAgRlVOQyg0LDYxKTsg IEZVTkMoNCw2Mik7ICBGVU5DKDQsNjMpOyAgRlVOQyg0LDY0KTsNCiAgICBG VU5DKDQsNjUpOyAgRlVOQyg0LDY2KTsgIEZVTkMoNCw2Nyk7ICBGVU5DKDQs NjgpOyAgRlVOQyg0LDY5KTsNCiAgICBGVU5DKDQsNzApOyAgRlVOQyg0LDcx KTsgIEZVTkMoNCw3Mik7ICBGVU5DKDQsNzMpOyAgRlVOQyg0LDc0KTsNCiAg ICBGVU5DKDQsNzUpOyAgRlVOQyg0LDc2KTsgIEZVTkMoNCw3Nyk7ICBGVU5D KDQsNzgpOyAgRlVOQyg0LDc5KTsNCiNlbHNlIC8qICFVTlJPTExfTE9PUFMg Ki8NCiAgICBmb3IgKGkgPSAwOyBpIDwgMjA7ICsraSkgew0KCUZVTkMoMSxp KTsNCiAgICB9DQogICAgZm9yIChpID0gMjA7IGkgPCA0MDsgKytpKSB7DQoJ RlVOQygyLGkpOw0KICAgIH0NCiAgICBmb3IgKGkgPSA0MDsgaSA8IDYwOyAr K2kpIHsNCglGVU5DKDMsaSk7DQogICAgfQ0KICAgIGZvciAoaSA9IDYwOyBp IDwgODA7ICsraSkgew0KCUZVTkMoNCxpKTsNCiAgICB9DQojZW5kaWYgLyog IVVOUk9MTF9MT09QUyAqLw0KICAgIHNoYV9pbmZvLT5kaWdlc3RbMF0gKz0g QTsNCiAgICBzaGFfaW5mby0+ZGlnZXN0WzFdICs9IEI7DQogICAgc2hhX2lu Zm8tPmRpZ2VzdFsyXSArPSBDOw0KICAgIHNoYV9pbmZvLT5kaWdlc3RbM10g Kz0gRDsNCiAgICBzaGFfaW5mby0+ZGlnZXN0WzRdICs9IEU7DQp9DQoNCnVu aW9uIGVuZGlhblRlc3Qgew0KICBsb25nIExvbmc7DQogIGNoYXIgQ2hhcltz aXplb2YobG9uZyldOw0KfTsNCg0KY2hhciBpc0xpdHRsZUVuZGlhbigpIHsN CiAgc3RhdGljIHVuaW9uIGVuZGlhblRlc3QgdTsNCiAgdS5Mb25nID0gMTsN CiAgcmV0dXJuKHUuQ2hhclswXT09MSk7DQp9DQoNCi8qIGNoYW5nZSBlbmRp YW5uZXNzIG9mIGRhdGEgKi8NCg0KLyogY291bnQgaXMgdGhlIG51bWJlciBv ZiBieXRlcyB0byBkbyBhbiBlbmRpYW4gZmxpcCAqLw0Kc3RhdGljIHZvaWQg bWF5YmVfYnl0ZV9yZXZlcnNlKExPTkcgKmJ1ZmZlciwgaW50IGNvdW50KQ0K ew0KICAgIGludCBpOw0KICAgIEJZVEUgY3RbNF0sICpjcDsNCg0KICAgIGlm IChpc0xpdHRsZUVuZGlhbigpKSB7ICAgIC8qIGRvIHRoZSBzd2FwIG9ubHkg aWYgaXQgaXMgbGl0dGxlIGVuZGlhbiAqLw0KICAgICAgY291bnQgLz0gc2l6 ZW9mKExPTkcpOw0KICAgICAgY3AgPSAoQllURSAqKSBidWZmZXI7DQogICAg ICBmb3IgKGkgPSAwOyBpIDwgY291bnQ7ICsraSkgew0KCSAgY3RbMF0gPSBj cFswXTsNCgkgIGN0WzFdID0gY3BbMV07DQoJICBjdFsyXSA9IGNwWzJdOw0K CSAgY3RbM10gPSBjcFszXTsNCgkgIGNwWzBdID0gY3RbM107DQoJICBjcFsx XSA9IGN0WzJdOw0KCSAgY3BbMl0gPSBjdFsxXTsNCgkgIGNwWzNdID0gY3Rb MF07DQoJICBjcCArPSBzaXplb2YoTE9ORyk7DQogICAgICB9DQogICAgfQ0K fQ0KDQovKiBpbml0aWFsaXplIHRoZSBTSEEgZGlnZXN0ICovDQoNCnZvaWQg c2hhX2luaXQoU0hBX0lORk8gKnNoYV9pbmZvKQ0Kew0KICAgIHNoYV9pbmZv LT5kaWdlc3RbMF0gPSAweDY3NDUyMzAxTDsNCiAgICBzaGFfaW5mby0+ZGln ZXN0WzFdID0gMHhlZmNkYWI4OUw7DQogICAgc2hhX2luZm8tPmRpZ2VzdFsy XSA9IDB4OThiYWRjZmVMOw0KICAgIHNoYV9pbmZvLT5kaWdlc3RbM10gPSAw eDEwMzI1NDc2TDsNCiAgICBzaGFfaW5mby0+ZGlnZXN0WzRdID0gMHhjM2Qy ZTFmMEw7DQogICAgc2hhX2luZm8tPmNvdW50X2xvID0gMEw7DQogICAgc2hh X2luZm8tPmNvdW50X2hpID0gMEw7DQogICAgc2hhX2luZm8tPmxvY2FsID0g MDsNCn0NCg0KLyogdXBkYXRlIHRoZSBTSEEgZGlnZXN0ICovDQoNCnZvaWQg c2hhX3VwZGF0ZShTSEFfSU5GTyAqc2hhX2luZm8sIEJZVEUgKmJ1ZmZlciwg aW50IGNvdW50KQ0Kew0KICAgIGludCBpOw0KDQogICAgaWYgKChzaGFfaW5m by0+Y291bnRfbG8gKyAoKExPTkcpIGNvdW50IDw8IDMpKSA8IHNoYV9pbmZv LT5jb3VudF9sbykgew0KCSsrc2hhX2luZm8tPmNvdW50X2hpOw0KICAgIH0N CiAgICBzaGFfaW5mby0+Y291bnRfbG8gKz0gKExPTkcpIGNvdW50IDw8IDM7 DQogICAgc2hhX2luZm8tPmNvdW50X2hpICs9IChMT05HKSBjb3VudCA+PiAy OTsNCiAgICBpZiAoc2hhX2luZm8tPmxvY2FsKSB7DQoJaSA9IFNIQV9CTE9D S1NJWkUgLSBzaGFfaW5mby0+bG9jYWw7DQoJaWYgKGkgPiBjb3VudCkgew0K CSAgICBpID0gY291bnQ7DQoJfQ0KCW1lbWNweSgoKEJZVEUgKikgc2hhX2lu Zm8tPmRhdGEpICsgc2hhX2luZm8tPmxvY2FsLCBidWZmZXIsIGkpOw0KCWNv dW50IC09IGk7DQoJYnVmZmVyICs9IGk7DQoJc2hhX2luZm8tPmxvY2FsICs9 IGk7DQoJaWYgKHNoYV9pbmZvLT5sb2NhbCA9PSBTSEFfQkxPQ0tTSVpFKSB7 DQoJICAgIG1heWJlX2J5dGVfcmV2ZXJzZShzaGFfaW5mby0+ZGF0YSwgU0hB X0JMT0NLU0laRSk7DQoJICAgIHNoYV90cmFuc2Zvcm0oc2hhX2luZm8pOw0K CX0gZWxzZSB7DQoJICAgIHJldHVybjsNCgl9DQogICAgfQ0KICAgIHdoaWxl IChjb3VudCA+PSBTSEFfQkxPQ0tTSVpFKSB7DQoJbWVtY3B5KHNoYV9pbmZv LT5kYXRhLCBidWZmZXIsIFNIQV9CTE9DS1NJWkUpOw0KCWJ1ZmZlciArPSBT SEFfQkxPQ0tTSVpFOw0KCWNvdW50IC09IFNIQV9CTE9DS1NJWkU7DQoJbWF5 YmVfYnl0ZV9yZXZlcnNlKHNoYV9pbmZvLT5kYXRhLCBTSEFfQkxPQ0tTSVpF KTsNCglzaGFfdHJhbnNmb3JtKHNoYV9pbmZvKTsNCiAgICB9DQogICAgbWVt Y3B5KHNoYV9pbmZvLT5kYXRhLCBidWZmZXIsIGNvdW50KTsNCiAgICBzaGFf aW5mby0+bG9jYWwgPSBjb3VudDsNCn0NCg0KLyogZmluaXNoIGNvbXB1dGlu ZyB0aGUgU0hBIGRpZ2VzdCAqLw0KDQp2b2lkIHNoYV9maW5hbChTSEFfSU5G TyAqc2hhX2luZm8pDQp7DQogICAgaW50IGNvdW50Ow0KICAgIExPTkcgbG9f Yml0X2NvdW50LCBoaV9iaXRfY291bnQ7DQoNCiAgICBsb19iaXRfY291bnQg PSBzaGFfaW5mby0+Y291bnRfbG87DQogICAgaGlfYml0X2NvdW50ID0gc2hh X2luZm8tPmNvdW50X2hpOw0KICAgIGNvdW50ID0gKGludCkgKChsb19iaXRf Y291bnQgPj4gMykgJiAweDNmKTsNCiAgICAoKEJZVEUgKikgc2hhX2luZm8t PmRhdGEpW2NvdW50KytdID0gMHg4MDsNCiAgICBpZiAoY291bnQgPiBTSEFf QkxPQ0tTSVpFIC0gOCkgew0KCW1lbXNldCgoKEJZVEUgKikgc2hhX2luZm8t PmRhdGEpICsgY291bnQsIDAsIFNIQV9CTE9DS1NJWkUgLSBjb3VudCk7DQoJ bWF5YmVfYnl0ZV9yZXZlcnNlKHNoYV9pbmZvLT5kYXRhLCBTSEFfQkxPQ0tT SVpFKTsNCglzaGFfdHJhbnNmb3JtKHNoYV9pbmZvKTsNCgltZW1zZXQoKEJZ VEUgKikgc2hhX2luZm8tPmRhdGEsIDAsIFNIQV9CTE9DS1NJWkUgLSA4KTsN CiAgICB9IGVsc2Ugew0KCW1lbXNldCgoKEJZVEUgKikgc2hhX2luZm8tPmRh dGEpICsgY291bnQsIDAsDQoJICAgIFNIQV9CTE9DS1NJWkUgLSA4IC0gY291 bnQpOw0KICAgIH0NCiAgICBtYXliZV9ieXRlX3JldmVyc2Uoc2hhX2luZm8t PmRhdGEsIFNIQV9CTE9DS1NJWkUpOw0KICAgIHNoYV9pbmZvLT5kYXRhWzE0 XSA9IGhpX2JpdF9jb3VudDsNCiAgICBzaGFfaW5mby0+ZGF0YVsxNV0gPSBs b19iaXRfY291bnQ7DQogICAgc2hhX3RyYW5zZm9ybShzaGFfaW5mbyk7DQoN Cn0NCg0KLyoNCiAgIGludGVybmFsbHkgaW1wbGVtZW50ZWQgYXMgYW4gYXJy YXkgb2YgbG9uZ3MsIG5lZWQgdG8gc3dhcCBpZiANCiAgIHlvdSdyZSBnb2lu ZyB0byBhY2Nlc3MgdGhlIG1lbW9yeSBpbiB0aGUgcmF3LCBpbnN0ZWFkIG9m IGxvb3BpbmcNCiAgIHRocm91Z2ggd2l0aCBhcnJheXMgb2YgbG9uZ3MuDQoq Lw0KDQp2b2lkIHNoYV9yYXdfc3dhcChTSEFfSU5GTyAqc2hhX2luZm8pIHsN CiAgaW50IGk7DQoNCiAgZm9yIChpPTA7IGk8NTsgKytpKQ0KICAgICBtYXli ZV9ieXRlX3JldmVyc2UoKExPTkcgKikgJnNoYV9pbmZvLT5kaWdlc3RbaV0s IDQpOw0KfQ0KDQpzdGF0aWMgY2hhciBiYXNpc182NFtdID0NCiAgIkFCQ0RF RkdISUpLTE1OT1BRUlNUVVZXWFlaYWJjZGVmZ2hpamtsbW5vcHFyc3R1dnd4 eXowMTIzNDU2Nzg5Ky8iOw0KDQp2b2lkIG91dHB1dDY0Y2h1bmsodW5zaWdu ZWQgY2hhciBjMSwgdW5zaWduZWQgY2hhciBjMiwgdW5zaWduZWQgY2hhciBj MywNCiAgICAgICAgICAgICAgICAgICBpbnQgcGFkcywgdW5zaWduZWQgY2hh ciAqKm91dGZpbGUpIHsNCg0KICAqKCpvdXRmaWxlKSsrID0gYmFzaXNfNjRb YzE+PjJdOw0KDQogICooKm91dGZpbGUpKysgPSBiYXNpc182NFsoKGMxICYg MHgzKTw8IDQpIHwgKChjMiAmIDB4RjApID4+IDQpXTsNCiAgaWYgKHBhZHMg PT0gMikgew0KICAgICooKm91dGZpbGUpKysgPSAnPSc7DQogICAgKigqb3V0 ZmlsZSkrKyA9ICc9JzsNCiAgfSBlbHNlIGlmIChwYWRzKSB7DQogICAgKigq b3V0ZmlsZSkrKyA9ICBiYXNpc182NFsoKGMyICYgMHhGKSA8PCAyKSB8ICgo YzMgJiAweEMwKSA+PjYpXTsNCiAgICAqKCpvdXRmaWxlKSsrID0gJz0nOw0K ICB9IGVsc2Ugew0KICAgICooKm91dGZpbGUpKysgPSBiYXNpc182NFsoKGMy ICYgMHhGKSA8PCAyKSB8ICgoYzMgJiAweEMwKSA+PjYpXTsNCiAgICAqKCpv dXRmaWxlKSsrID0gYmFzaXNfNjRbYzMgJiAweDNGXTsNCiAgfQ0KfQ0KDQp2 b2lkIGVuY29kZV9taW1lNjQodW5zaWduZWQgY2hhciAqaW4sIHVuc2lnbmVk IGNoYXIgKm91dCwgaW50IGxlbmd0aCkgew0KICBpbnQgZGlmZiwgY3Q9MDsN Cg0KICB3aGlsZSAoIChkaWZmPSBsZW5ndGggLSBjdCkgKSB7DQogICAgaWYg KCBkaWZmID49IDMgKSB7DQogICAgICBkaWZmID0gMzsNCiAgICAgIG91dHB1 dDY0Y2h1bmsoaW5bY3RdLCBpbltjdCsxXSwgaW5bY3QrMl0sIDAsICZvdXQp Ow0KICAgIH0NCiAgICBlbHNlIGlmICggZGlmZiA9PSAyICkgew0KICAgICAg b3V0cHV0NjRjaHVuayhpbltjdF0sIGluW2N0KzFdLCAwLCAxLCAmb3V0KTsN CiAgICB9DQogICAgZWxzZSBpZiAoIGRpZmYgPT0gMSApIHsNCiAgICAgIG91 dHB1dDY0Y2h1bmsoaW5bY3RdLCAwLCAwLCAyLCAmb3V0KTsNCiAgICB9DQog ICAgY3QgKz0gZGlmZjsNCiAgfQ0KDQogICpvdXQrKyA9IDA7DQp9DQoNCkFQ SV9FWFBPUlQodm9pZCkgYXBfc2hhMV9iYXNlNjQoY2hhciAqY2xlYXIsIGlu dCBsZW4sIGNoYXIgKm91dCkgIHsNCiAgU0hBX0lORk8gY29udGV4dDsNCiAg c2hhX2luaXQoJmNvbnRleHQpOw0KICBzaGFfdXBkYXRlKCZjb250ZXh0LCBj bGVhciwgbGVuKTsNCiAgc2hhX2ZpbmFsKCZjb250ZXh0KTsNCiAgDQogIHNo YV9yYXdfc3dhcCgmY29udGV4dCk7DQoNCiAgLyogU0hBMSBoYXNoIGlzIGFs d2F5cyAyMCBjaGFycyAqLw0KICBlbmNvZGVfbWltZTY0KChjaGFyICopY29u dGV4dC5kaWdlc3QsIG91dCwgMjApOw0KDQogIC8qIG91dHB1dCBvZiBNSU1F IEJhc2UgNjQgZW5jb2RlZCBTSEExIGlzIGFsd2F5cyAyOCBjaGFyYWN0ZXJz ICovDQp9DQo= --0-1671077389-933518935=:16065--