[Zope-dev] Subclassing ExtensionClass in C (this time with a solution)

James Henstridge james@daa.com.au
Fri, 3 Mar 2000 13:21:11 +0800 (WST)


  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.

--298516987-757284759-952060871=:28581
Content-Type: TEXT/PLAIN; charset=US-ASCII

Last week I asked a question about subclassing ExtensionClasses in C, but
no one seemed to know how to do it.  I then tried asking Jim Fulton about
it, but he hasn't responded yet.

So I decided to sit down and try to add the functionality myself.  I am
posting it here as some people on the list expressed an interest.  I have
tried to keep to the style of the current code, so those who have used
ExtensionClass should be able to do Extension Subclasses in C without too
much problem.  Also, the modification is backward compatible (both source
and binary), so it shouldn't break any current code.

The one place where the programmer has to be careful is in making the
size and layout of the instance structure of the new class is compatible
with its base classes.  I didn't include the checks done when subclassing
from python, as you may want to have more than one non-pure mixin base
class, or to extend the size of the instance structure in the subclass.

To define a new Extension Subclass, follow the same steps as for a normal
ExtensionClass, but instead of using PyExtensionClass_Export, use
PyExtensionClass_ExportSubclass.  This new function is similar to
PyExtensionClass_Export, except that it takes an extra argument -- a tuple
of base classes.  The function takes ownership of the tuple.

In cases where you only want to do single inheritance, there is a
convenience routine called PyExtensionClass_ExportSubclassSingle.  Its
last argument is the PyExtensionClass structure for the base class.

I have also attached a test module called TESC that tests out subclassing
in C.  Running it gives output something like:
>>> import TESC
>>> a = TESC.Cls()
>>> b = TESC.Subcls()
>>> a.m1(), a.m2()
('m1 of Cls called', 'm2 of Cls called')
>>> b.m1(), b.m2(), b.m3()
('m1 of Subcls called', 'm2 of Cls called', 'm3 of Subcls called')

I have tested this module a fair amount, and it doesn't seem to introduce
any problems with existing code, and is a fairly clean modification (I
could have made the change a little cleaner, but that would have broken
binary compatibility).  So I was wondering if my patch could be integrated
into the official ExtensionClass distribution.  I am sure it is of use to
more people than just me.

James.

--
Email: james@daa.com.au
WWW:   http://www.daa.com.au/~james/


--298516987-757284759-952060871=:28581
Content-Type: TEXT/PLAIN; charset=US-ASCII; name="ec-subclass.patch"
Content-Transfer-Encoding: BASE64
Content-ID: <Pine.LNX.3.96.1000303132111.28581E@quoll.daa.com.au>
Content-Description: ExtensionClass patch

LS0tIEV4dGVuc2lvbkNsYXNzLmMub3JpZwlGcmkgTWFyICAzIDA5OjE3OjM1
IDIwMDANCisrKyBFeHRlbnNpb25DbGFzcy5jCUZyaSBNYXIgIDMgMTI6MjA6
MzkgMjAwMA0KQEAgLTE1NzEsNyArMTU3MSw4IEBADQogICBmcHJpbnRmKHN0
ZGVyciwiRGVhbGxvY2F0aW5nICVzXG4iLCBzZWxmLT50cF9uYW1lKTsNCiAj
ZW5kaWYNCiAgIFB5X1hERUNSRUYoc2VsZi0+Y2xhc3NfZGljdGlvbmFyeSk7
DQotICBpZiAoc2VsZi0+YmFzZXMpDQorICAvKiBpZiB0aGlzIEV4dGVuc2lv
bkNsYXNzIHdhcyBzdWJjbGFzc2VkIGluIHB5dGhvbiwgZnJlZSB0aGlzIGlu
Zm8gKi8NCisgIGlmICgoc2VsZi0+Y2xhc3NfZmxhZ3MgJiBFWFRFTlNJT05D
TEFTU19QWVNVQkNMQVNTX0ZMQUcpICE9IDApDQogICAgIHsNCiAgICAgICAv
KiBJZiB3ZSBhcmUgYSBzdWJjbGFzcywgdGhlbiB3ZSBzdHJkdXBlZCBvdXIg
bmFtZSAqLw0KICAgICAgIGZyZWUoc2VsZi0+dHBfbmFtZSk7DQpAQCAtMTU4
MCw5ICsxNTgxLDggQEANCiAgICAgICBpZiAoc2VsZi0+dHBfYXNfbnVtYmVy
KSAgIGZyZWUoc2VsZi0+dHBfYXNfbnVtYmVyKTsNCiAgICAgICBpZiAoc2Vs
Zi0+dHBfYXNfc2VxdWVuY2UpIGZyZWUoc2VsZi0+dHBfYXNfc2VxdWVuY2Up
Ow0KICAgICAgIGlmIChzZWxmLT50cF9hc19tYXBwaW5nKSAgZnJlZShzZWxm
LT50cF9hc19tYXBwaW5nKTsNCi0gICAgICANCi0gICAgICBQeV9ERUNSRUYo
c2VsZi0+YmFzZXMpOw0KICAgICB9DQorICBQeV9YREVDUkVGKHNlbGYtPmJh
c2VzKTsNCiAgIGlmICgoKFB5RXh0ZW5zaW9uQ2xhc3MqKXNlbGYtPm9iX3R5
cGUpICE9IHNlbGYpIFB5X1hERUNSRUYoc2VsZi0+b2JfdHlwZSk7DQogICBQ
eU1lbV9ERUwoc2VsZik7DQogfQ0KQEAgLTMyNDEsNiArMzI0MSw5IEBADQog
I2RlZmluZSBjb3B5X21lbWJlcihNKSBzZWxmLT5NPXR5cGUtPk0NCiAgIGNv
cHlfbWVtYmVyKG9iX3NpemUpOw0KICAgY29weV9tZW1iZXIoY2xhc3NfZmxh
Z3MpOw0KKyAgLyogbWFyayBzdWJjbGFzcyBhcyBhIHB5dGhvbiBvbmUsIHNv
IHN1YmNsYXNzIHN0cnVjdHVyZXMgYXJlIGZyZWVkIG9uDQorICAgKiBkZWFs
bG9jYXRpb24gKi8NCisgIHNlbGYtPmNsYXNzX2ZsYWdzIHw9IEVYVEVOU0lP
TkNMQVNTX1BZU1VCQ0xBU1NfRkxBRzsNCiANCiAgIGNvcHlfbWVtYmVyKHRw
X2l0ZW1zaXplKTsNCiAgIGNvcHlfbWVtYmVyKHRwX3ByaW50KTsNCkBAIC0z
Mzk5LDYgKzM0MDIsMzYgQEANCiAgIHJldHVybiBQeU1hcHBpbmdfU2V0SXRl
bVN0cmluZyhkaWN0LG5hbWUsKFB5T2JqZWN0Kil0eXApOw0KIH0NCiANCisv
KiBiYXNlcyBpcyBhIHR1cGxlIG9mIGJhc2UgY2xhc3Nlcy4gIFRoaXMgZnVu
Y3Rpb24gYWJzb3JicyB0aGUgcmVmZXJlbmNlICovDQorc3RhdGljIGludA0K
K2V4cG9ydF9zdWJjbGFzc2VkX3R5cGUoUHlPYmplY3QgKmRpY3QsIGNoYXIg
Km5hbWUsIFB5RXh0ZW5zaW9uQ2xhc3MgKnR5cCwNCisJCSAgICAgICBQeU9i
amVjdCAqYmFzZXMpDQorew0KKyAgaW5pdGlhbGl6ZUJhc2VFeHRlbnNpb25D
bGFzcyh0eXApOw0KKw0KKyAgaWYgKFB5RXJyX09jY3VycmVkKCkpIHJldHVy
biAtMTsNCisNCisgIC8qIHNldCB0aGlzIHVwIGFzIGEgc3ViY2xhc3NlZCBF
eHRlbnNpb25DbGFzcyAqLw0KKyAgVU5MRVNTIChiYXNlcyAmJiBQeVR1cGxl
X0NoZWNrKGJhc2VzKSAmJiBQeVR1cGxlX1NpemUoYmFzZXMpKSB7DQorICAg
IFB5RXJyX1NldFN0cmluZyhQeUV4Y19UeXBlRXJyb3IsDQorCQkic2Vjb25k
IGFyZ3VtZW50IG11c3QgYmUgYSB0dXBsZSBvZiAxIG9yIG1vcmUgYmFzZSBj
bGFzc2VzIik7DQorICAgIHJldHVybiAtMTsNCisgIH0NCisgIHR5cC0+YmFz
ZXMgPSBiYXNlczsNCisNCisgIGlmIChQeURpY3RfR2V0SXRlbSh0eXAtPmNs
YXNzX2RpY3Rpb25hcnksIHB5X19tb2R1bGVfXykgPT0gTlVMTCkNCisgICAg
ew0KKyAgICAgIFB5T2JqZWN0ICptb2RuYW1lID0gUHlEaWN0X0dldEl0ZW0o
ZGljdCwgcHlfX25hbWVfXyk7DQorICAgICAgaWYgKG1vZG5hbWUgIT0gTlVM
TCkgew0KKwlpZiAoUHlEaWN0X1NldEl0ZW0odHlwLT5jbGFzc19kaWN0aW9u
YXJ5LCBweV9fbW9kdWxlX18sIG1vZG5hbWUpIDwgMCkNCisJICByZXR1cm4g
LTE7DQorICAgICAgfQ0KKyAgICB9DQorICBQeUVycl9DbGVhcigpOw0KKyAg
DQorICByZXR1cm4gUHlNYXBwaW5nX1NldEl0ZW1TdHJpbmcoZGljdCxuYW1l
LChQeU9iamVjdCopdHlwKTsNCit9DQorDQogc3RhdGljIHN0cnVjdCBFeHRl
bnNpb25DbGFzc0NBUElzdHJ1Y3QNCiBUcnVlRXh0ZW5zaW9uQ2xhc3NDQVBJ
ID0gew0KICAgZXhwb3J0X3R5cGUsDQpAQCAtMzQxMCw2ICszNDQzLDcgQEAN
CiAgIChQeU9iamVjdCopJlBNZXRob2RUeXBlLA0KICAgUE1ldGhvZF9OZXcs
DQogICBDTWV0aG9kX2lzc3ViY2xhc3MsDQorICBleHBvcnRfc3ViY2xhc3Nl
ZF90eXBlLA0KIH07DQogDQogdm9pZA0KLS0tIEV4dGVuc2lvbkNsYXNzLmgu
b3JpZwlGcmkgTWFyICAzIDA5OjE3OjQxIDIwMDANCisrKyBFeHRlbnNpb25D
bGFzcy5oCUZyaSBNYXIgIDMgMTI6MTM6MjQgMjAwMA0KQEAgLTE3NCw2ICsx
NzQsNyBAQA0KICNkZWZpbmUgRVhURU5TSU9OQ0xBU1NfSU5TVERJQ1RfRkxB
RyAgICAgIDEgPDwgNA0KICNkZWZpbmUgRVhURU5TSU9OQ0xBU1NfTk9JTlNU
RElDVF9GTEFHICAgIDEgPDwgNQ0KICNkZWZpbmUgRVhURU5TSU9OQ0xBU1Nf
QkFTSUNORVdfRkxBRyAgICAgIDEgPDwgNg0KKyNkZWZpbmUgRVhURU5TSU9O
Q0xBU1NfUFlTVUJDTEFTU19GTEFHICAgIDEgPDwgNw0KIA0KICAgLyogVGhl
IGZvbGxvd2luZyBmbGFncyBhcmUgZm9yIHVzZSBieSBleHRlbnNpb24gY2xh
c3MgZGV2ZWxvcGVycy4gKi8NCiAjZGVmaW5lIEVYVEVOU0lPTkNMQVNTX1VT
RVJfRkxBRzEgIAkgIDEgPDwgMTYNCkBAIC0yOTcsNiArMjk4LDI1IEBADQog
ICAgICAgICAgICAgICAgICAgICAgICAgICBQeUNPYmplY3RfSW1wb3J0KCJF
eHRlbnNpb25DbGFzcyIsIkNBUEkiKSkpIFwNCiAgICB7IFB5RXh0ZW5zaW9u
Q2xhc3NDQVBJLT5FeHBvcnQoRCxOLCZUKTsgfQ0KIA0KKy8qIEV4cG9ydCBh
biBFeHRlbnNpb24gU3ViY2xhc3MgY2xhc3MgaW4gYSBnaXZlbiBtb2R1bGUg
ZGljdGlvbmFyeSB3aXRoIGENCisgICBnaXZlbiBuYW1lLCBFeHRlbnNpb25D
bGFzcyBzdHJ1Y3R1cmUgYW5kIHNldCBvZiBiYXNlIGNsYXNzZXMuICBJdCBp
cw0KKyAgIHVwIHRvIHRoZSBwcm9ncmFtbWVyIHRvIG1ha2Ugc3VyZSB0aGF0
IHRoZSBpbnN0YW5jZSBzdHJ1Y3R1cmVzIG9mIHRoZQ0KKyAgIGJhc2UgY2xh
c3NlcyBhcmUgY29tcGF0aWJsZSB3aXRoIHRoYXQgb2YgdGhlIG5ldyBjbGFz
cy4NCisgICAqLw0KKyNkZWZpbmUgUHlFeHRlbnNpb25DbGFzc19FeHBvcnRT
dWJjbGFzcyhELE4sVCxCKSBcDQorIGlmKFB5RXh0ZW5zaW9uQ2xhc3NDQVBJ
IHx8IFwNCisgICAoUHlFeHRlbnNpb25DbGFzc0NBUEk9IChzdHJ1Y3QgRXh0
ZW5zaW9uQ2xhc3NDQVBJc3RydWN0KikgXA0KKyAgICAgICAgICAgICAgICAg
ICAgICAgICAgUHlDT2JqZWN0X0ltcG9ydCgiRXh0ZW5zaW9uQ2xhc3MiLCJD
QVBJIikpKSBcDQorICAgeyBQeUV4dGVuc2lvbkNsYXNzQ0FQSS0+RXhwb3J0
U3ViY2xhc3MoRCxOLCZULEIpOyB9DQorDQorLyogRXhwb3J0IGFuIEV4dGVu
c2lvbiBTdWJjbGFzcyBjbGFzcyBpbiBhIGdpdmVuIG1vZHVsZSBkaWN0aW9u
YXJ5IHdpdGggYQ0KKyAgIGdpdmVuIG5hbWUsIEV4dGVuc2lvbkNsYXNzIHN0
cnVjdHVyZSBhbmQgc2luZ2xlIGJhc2UgY2xhc3MuIEl0IGlzIHVwIHRvDQor
ICAgdGhlIHByb2dyYW1tZXIgdG8gbWFrZSBzdXJlIHRoYXQgdGhlIGluc3Rh
bmNlIHN0cnVjdHVyZXMgb2YgdGhlIGJhc2UNCisgICBjbGFzc2VzIGFyZSBj
b21wYXRpYmxlIHdpdGggdGhhdCBvZiB0aGUgbmV3IGNsYXNzLg0KKyAgICov
DQorI2RlZmluZSBQeUV4dGVuc2lvbkNsYXNzX0V4cG9ydFN1YmNsYXNzU2lu
Z2xlKEQsTixULEIpIFwNCisgIFB5RXh0ZW5zaW9uQ2xhc3NfRXhwb3J0U3Vi
Y2xhc3MoRCwgTiwgVCwgUHlfQnVpbGRWYWx1ZSgiKE8pIiwoUHlPYmplY3Qq
KSZCKSkNCisNCiAvKiBDb252ZXJ0IGEgbWV0aG9kIGxpc3QgdG8gYSBtZXRo
b2QgY2hhaW4uICAqLw0KICNkZWZpbmUgTUVUSE9EX0NIQUlOKERFRikgeyBE
RUYsIE5VTEwgfQ0KIA0KQEAgLTQxMSw2ICs0MzEsOCBAQA0KICAgUHlPYmpl
Y3QgKk1ldGhvZFR5cGU7DQogICBQeU9iamVjdCAqKCpNZXRob2RfTmV3KShQ
eU9iamVjdCAqY2FsbGFibGUsIFB5T2JqZWN0ICppbnN0KTsNCiAgIGludCAo
Kmlzc3ViY2xhc3MpKFB5RXh0ZW5zaW9uQ2xhc3MgKnN1YiwgUHlFeHRlbnNp
b25DbGFzcyAqdHlwZSk7DQorICBpbnQgKCpFeHBvcnRTdWJjbGFzcykoUHlP
YmplY3QgKmRpY3QsIGNoYXIgKm5hbWUsDQorCQkJUHlFeHRlbnNpb25DbGFz
cyAqb2JfdHlwZSwgUHlPYmplY3QgKmJhc2VzKTsNCiB9ICpQeUV4dGVuc2lv
bkNsYXNzQ0FQSSA9IE5VTEw7DQogDQogdHlwZWRlZiBzdHJ1Y3QgeyBQeU9i
amVjdF9IRUFEIH0gUHlQdXJlTWl4aW5PYmplY3Q7DQo=
--298516987-757284759-952060871=:28581
Content-Type: TEXT/PLAIN; charset=US-ASCII; name="TESC.c"
Content-Transfer-Encoding: BASE64
Content-ID: <Pine.LNX.3.96.1000303132111.28581F@quoll.daa.com.au>
Content-Description: Test for Extension Subclasses

LyogVEVTQyAtLSBUZXN0IEV4dGVuc2lvblN1YkNsYXNzLiAgSSBrbm93IGl0
IGlzIG5vdCBhIGdyZWF0IG5hbWUgOikgKi8NCg0KI2luY2x1ZGUgIkV4dGVu
c2lvbkNsYXNzLmgiDQoNCnN0YXRpY2ZvcndhcmQgUHlFeHRlbnNpb25DbGFz
cyBDbHNUeXBlOw0Kc3RhdGljZm9yd2FyZCBQeUV4dGVuc2lvbkNsYXNzIFN1
YmNsc1R5cGU7DQoNCnN0YXRpYyB2b2lkDQpkZWFsbG9jKFB5T2JqZWN0ICpz
ZWxmKQ0Kew0KICBQeU1lbV9ERUwoc2VsZik7DQp9DQoNCnN0YXRpYyBQeU9i
amVjdCAqDQpnZXRhdHRyKFB5T2JqZWN0ICpzZWxmLCBjaGFyICphdHRyKQ0K
ew0KICByZXR1cm4gUHlfRmluZE1ldGhvZChjbHNfbWV0aG9kcywgc2VsZiwg
YXR0cik7DQp9DQoNCnN0YXRpYyBQeU9iamVjdCAqDQpjbHNfbTEoUHlPYmpl
Y3QgKnNlbGYsIFB5T2JqZWN0ICphcmdzKQ0Kew0KICByZXR1cm4gUHlTdHJp
bmdfRnJvbVN0cmluZygibTEgb2YgQ2xzIGNhbGxlZCIpOw0KfQ0KDQpzdGF0
aWMgUHlPYmplY3QgKg0KY2xzX20yKFB5T2JqZWN0ICpzZWxmLCBQeU9iamVj
dCAqYXJncykNCnsNCiAgcmV0dXJuIFB5U3RyaW5nX0Zyb21TdHJpbmcoIm0y
IG9mIENscyBjYWxsZWQiKTsNCn0NCg0Kc3RhdGljIHN0cnVjdCBQeU1ldGhv
ZERlZiBjbHNfbWV0aG9kc1tdID0gew0KICB7Im0xIiwgKFB5Q0Z1bmN0aW9u
KWNsc19tMSwgMSwgIiJ9LA0KICB7Im0yIiwgKFB5Q0Z1bmN0aW9uKWNsc19t
MiwgMSwgIiJ9LA0KICB7TlVMTCwgTlVMTH0NCn07DQoNCg0Kc3RhdGljIFB5
T2JqZWN0ICoNCnN1Yl9tMShQeU9iamVjdCAqc2VsZiwgUHlPYmplY3QgKmFy
Z3MpDQp7DQogIHJldHVybiBQeVN0cmluZ19Gcm9tU3RyaW5nKCJtMSBvZiBT
dWJjbHMgY2FsbGVkIik7DQp9DQoNCnN0YXRpYyBQeU9iamVjdCAqDQpzdWJf
bTMoUHlPYmplY3QgKnNlbGYsIFB5T2JqZWN0ICphcmdzKQ0Kew0KICByZXR1
cm4gUHlTdHJpbmdfRnJvbVN0cmluZygibTMgb2YgU3ViY2xzIGNhbGxlZCIp
Ow0KfQ0KDQpzdGF0aWMgc3RydWN0IFB5TWV0aG9kRGVmIHN1Yl9tZXRob2Rz
W10gPSB7DQogIHsibTEiLCAoUHlDRnVuY3Rpb24pc3ViX20xLCAxLCAiIn0s
DQogIHsibTMiLCAoUHlDRnVuY3Rpb24pc3ViX20zLCAxLCAiIn0sDQogIHtO
VUxMLCBOVUxMfQ0KfTsNCg0Kc3RhdGljIFB5RXh0ZW5zaW9uQ2xhc3MgQ2xz
VHlwZSA9IHsNCiAgUHlPYmplY3RfSEVBRF9JTklUKE5VTEwpDQogIDAsICAg
ICAgICAgICAgICAgICAgICAgICAgICAgIC8qb2Jfc2l6ZSovDQogICJDbHMi
LCAgICAgICAgICAgICAgICAgICAgICAgIC8qdHBfbmFtZSovDQogIHNpemVv
ZihQeUV4dGVuc2lvbkNsYXNzKSwgICAgIC8qdHBfYmFzaWNzaXplKi8NCiAg
MCwgICAgICAgICAgICAgICAgICAgICAgICAgICAgLyp0cF9pdGVtc2l6ZSov
DQogIC8qIG1ldGhvZHMgKi8NCiAgKGRlc3RydWN0b3IpZGVhbGxvYywgICAg
ICAgICAgLyp0cF9kZWFsbG9jKi8NCiAgKHByaW50ZnVuYykwLCAgICAgICAg
ICAgICAgICAgLyp0cF9wcmludCovDQogIChnZXRhdHRyZnVuYylnZXRhdHRy
LCAgICAgICAgIC8qdHBfZ2V0YXR0ciovDQogIChzZXRhdHRyZnVuYykwLCAg
ICAgICAgICAgICAgIC8qdHBfc2V0YXR0ciovDQogIChjbXBmdW5jKTAsICAg
ICAgICAgICAgICAgICAgIC8qdHBfY29tcGFyZSovDQogIChyZXByZnVuYykw
LCAgICAgICAgICAgICAgICAgIC8qdHBfcmVwciovDQogIDAsICAgICAgICAg
ICAgICAgICAgICAgICAgICAgIC8qdHBfYXNfbnVtYmVyKi8NCiAgMCwgICAg
ICAgICAgICAgICAgICAgICAgICAgICAgLyp0cF9hc19zZXF1ZW5jZSovDQog
IDAsICAgICAgICAgICAgICAgICAgICAgICAgICAgIC8qdHBfYXNfbWFwcGlu
ZyovDQogIChoYXNoZnVuYykwLCAgICAgICAgICAgICAgICAgIC8qdHBfaGFz
aCovDQogICh0ZXJuYXJ5ZnVuYykwLCAgICAgICAgICAgICAgIC8qdHBfY2Fs
bCovDQogIChyZXByZnVuYykwLCAgICAgICAgICAgICAgICAgIC8qdHBfc3Ry
Ki8NCiAgKGdldGF0dHJvZnVuYykwLCAgIC8qdHBfZ2V0YXR0ciB3aXRoIG9i
amVjdCBrZXkqLw0KICAoc2V0YXR0cm9mdW5jKTAsICAgLyp0cF9zZXRhdHRy
IHdpdGggb2JqZWN0IGtleSovDQogIC8qIFNwYWNlIGZvciBmdXR1cmUgZXhw
YW5zaW9uICovDQogIDBMLDBMLA0KICBOVUxMLCAvKiBEb2N1bWVudGF0aW9u
IHN0cmluZyAqLw0KICBNRVRIT0RfQ0hBSU4oY2xzX21ldGhvZHMpDQp9Ow0K
c3RhdGljIFB5RXh0ZW5zaW9uQ2xhc3MgU3ViY2xzVHlwZSA9IHsNCiAgUHlP
YmplY3RfSEVBRF9JTklUKE5VTEwpDQogIDAsICAgICAgICAgICAgICAgICAg
ICAgICAgICAgIC8qb2Jfc2l6ZSovDQogICJTdWJjbHMiLCAgICAgICAgICAg
ICAgICAgICAgIC8qdHBfbmFtZSovDQogIHNpemVvZihQeUV4dGVuc2lvbkNs
YXNzKSwgICAgIC8qdHBfYmFzaWNzaXplKi8NCiAgMCwgICAgICAgICAgICAg
ICAgICAgICAgICAgICAgLyp0cF9pdGVtc2l6ZSovDQogIC8qIG1ldGhvZHMg
Ki8NCiAgKGRlc3RydWN0b3IpZGVhbGxvYywgICAgICAgICAgLyp0cF9kZWFs
bG9jKi8NCiAgKHByaW50ZnVuYykwLCAgICAgICAgICAgICAgICAgLyp0cF9w
cmludCovDQogIChnZXRhdHRyZnVuYylnZXRhdHRyLCAgICAgICAgIC8qdHBf
Z2V0YXR0ciovDQogIChzZXRhdHRyZnVuYykwLCAgICAgICAgICAgICAgIC8q
dHBfc2V0YXR0ciovDQogIChjbXBmdW5jKTAsICAgICAgICAgICAgICAgICAg
IC8qdHBfY29tcGFyZSovDQogIChyZXByZnVuYykwLCAgICAgICAgICAgICAg
ICAgIC8qdHBfcmVwciovDQogIDAsICAgICAgICAgICAgICAgICAgICAgICAg
ICAgIC8qdHBfYXNfbnVtYmVyKi8NCiAgMCwgICAgICAgICAgICAgICAgICAg
ICAgICAgICAgLyp0cF9hc19zZXF1ZW5jZSovDQogIDAsICAgICAgICAgICAg
ICAgICAgICAgICAgICAgIC8qdHBfYXNfbWFwcGluZyovDQogIChoYXNoZnVu
YykwLCAgICAgICAgICAgICAgICAgIC8qdHBfaGFzaCovDQogICh0ZXJuYXJ5
ZnVuYykwLCAgICAgICAgICAgICAgIC8qdHBfY2FsbCovDQogIChyZXByZnVu
YykwLCAgICAgICAgICAgICAgICAgIC8qdHBfc3RyKi8NCiAgKGdldGF0dHJv
ZnVuYykwLCAgIC8qdHBfZ2V0YXR0ciB3aXRoIG9iamVjdCBrZXkqLw0KICAo
c2V0YXR0cm9mdW5jKTAsICAgLyp0cF9zZXRhdHRyIHdpdGggb2JqZWN0IGtl
eSovDQogIC8qIFNwYWNlIGZvciBmdXR1cmUgZXhwYW5zaW9uICovDQogIDBM
LDBMLA0KICBOVUxMLCAvKiBEb2N1bWVudGF0aW9uIHN0cmluZyAqLw0KICBN
RVRIT0RfQ0hBSU4oc3ViX21ldGhvZHMpDQp9Ow0KDQpzdGF0aWMgc3RydWN0
IFB5TWV0aG9kRGVmIG1ldGhvZHNbXSA9IHt7TlVMTCwgICBOVUxMfX07DQoN
CnZvaWQgaW5pdFRFU0MoKQ0Kew0KICBQeU9iamVjdCAqbSwgKmQ7DQoNCiAg
bSA9IFB5X0luaXRNb2R1bGUoIlRFU0MiLCBtZXRob2RzKTsNCiAgZCA9IFB5
TW9kdWxlX0dldERpY3QobSk7DQoNCiAgUHlFeHRlbnNpb25DbGFzc19FeHBv
cnQoZCwgIkNscyIsIENsc1R5cGUpOw0KICBQeUV4dGVuc2lvbkNsYXNzX0V4
cG9ydFN1YmNsYXNzU2luZ2xlKGQsICJTdWJjbHMiLCBTdWJjbHNUeXBlLCBD
bHNUeXBlKTsNCn0NCg==
--298516987-757284759-952060871=:28581--