diff --git a/bin/types/alotofkeys.json b/bin/types/alotofkeys.json new file mode 100644 index 000000000..3fc052e34 --- /dev/null +++ b/bin/types/alotofkeys.json @@ -0,0 +1,502 @@ +{ + "4BABQZ5SZJSO3KFKBOG36EIXXTOF34HVFCELHA2DWOMIL44K": null, + "RSZNOTRIJFCHRKG4IKNOW4ZEBMVXPDBYBXBGDGNWTSVLMJ2U": null, + "AOGQPY32FQ7T7WZWQPON3X6GU74GOYI6HHVNPATDTBXRUQ4G": null, + "3PMTZEGLZNHSOWWJ23BE6PWOXD2VZRDN7MMLUMQ4EIRERVCG": null, + "PD2FMQGI5HTGK6MT76OYS2ER2LXFBON44WOMELDY5MRKQI6I": null, + "6L6QMMVSE4UQLB4OGX3LVDRNGAL6MOJ6S3RBBUSQ3F5PPHYR": null, + "LYVVXT7U7WN7PGGUHCLFXVOBJBSSR6ES2P7AY7XGBXEBLTDD": null, + "G5RWOLHDDZOXYEFGGSVWG3C2UHYDW6UOFVBQQLQJVZNCF4TB": null, + "3QPIK2M3ZPICZQFQTX22A7VDCAFIGAX2PXIXKDOZX7XUM32R": null, + "JR75L2BXOA5LVLNKT4EEZO2P45OHWRPMMWMFENTFFIY7A2V3": null, + "TESL546MN7IR7AT3C5HRSESIFHZ5NW6TNRWZXZ43OSRYOZKP": null, + "62EJKIAFWGFGPUS6YP2X6E26AV2TZCTCAJMZNWBBNFRPCCRN": null, + "5ZDD3KPTPGE2CAWR3MTFUSBMGQAS4ZP5WZKXJTXUNFSYABD6": null, + "XQ7TMN5YMQLAND54B4VIVWJAHU3TNZKT2S4SVRW6WKHNJBX2": null, + "O456GV3HBAWFDQRCECX6HY3PBTP6WNQIDSKVP2MZIPV3TCBL": null, + "WXCN25EBQH5WWN2JBHWNFNDUTYSFDLIAOWO5AE6D5HDO7VNE": null, + "THO3I3KDRIMTD6DKNIETIOWDY7FXQ5GJ3P2KUQJWYAEL3LXV": null, + "7OMI7VIOKFRZATMNLGIWH7ZBDARZ6ARXIAH5S3GPG5KV52IC": null, + "ESUPY3ELKCEGFRSYFGPGFBJOAUGXMYZ6XCWXDFOKHBJHNGVR": null, + "TNXSJIEFJLUFUDTR2S5LV73PD6ACFYNHOCRZPUSDPXDD3B7M": null, + "T6TISG6P4W66F37634QU4BNJY4RZ77QXXNPGTYH5LCCRDSX6": null, + "QTVAA56JKNDYTMV7DXAIL4QVLZPW3UHGLTKDI2BED6S3MGDQ": null, + "DTJREAQBCS6I2AJ6MOGTPIXK3ADB4BPNDIHI2YSQP6Y2BMH7": null, + "XDGH2OYCTAJ75IEMZ32O644YLT73PRYDORFKBLYEMCHOQ7Q6": null, + "4KDDQZRBLNS33DRHZHDMENCWGMNFEJGBZJXSGIQW7VBWOTHT": null, + "5KSH3GKWFNXV55KI2FPUDSD57O25N52UTZAAYDFVMFUSEE6O": null, + "7AGEUBM5FQZ2JCMUSKTEI6COA3Q5CE5WYB7TP2F5OX3ETMTK": null, + "HFHZ5ZE5TC45W4WIF6H7ONTHXKAVWRY2LXN2GN2TXZPIP6PQ": null, + "S3U2JJBPKZHZNOM3SWVFQ7OMS7F5M2KDJHHHZKXHZXQRNUSE": null, + "YHJBGJ6T6A7PMK5AYXDITDV37BJJIM4TP7I2XHSVYN76724O": null, + "TH42A7M3645OUKC54JQMDB5BTGS3URFUCYJ2VOEM6IAGZ5QQ": null, + "OYBKULFLWL2MER745QTDL2X2HJNR77QGH2M2P6TSCHVGUJLV": null, + "JDU37GHQUOCYA5I5LFS3WAEKKR6C55XJCCLJCCCQJEGUJEP6": null, + "CB5HEJZNJ2SWZM426TWIWLHTWAPWPT2AVVHBILEVGFD6NPHI": null, + "D4A5SJA2VRB4JGJFC7PHT35S7XAMHPZZ2PZC5YYVV7RLKSUQ": null, + "BBVT6NRRU55KNRK5G745FNMZVIFHVZJICEMODF4ZBJFQ3EGL": null, + "XBV57OEMT4GYPTTH56A6XKF2ZPMXSMHY7L3LUIS5ZZWRP2OB": null, + "GTFJ3NP4VJR6HG2DRNTDKVIWTMIALYUQIQTBJMKVM2I3QKGE": null, + "77BMBFMRGASXE5XXT6BRH2DRBNJMIAUDDMEXIJT3RMHTUPI4": null, + "FWZZMG7I2JWAHX4LBYAK2G4L4TZYLHXMJWIDGT6JC5TEBCPJ": null, + "J3324OXU2BG2NGFMSOYMVKXE6OEJNGENI7EESHDSEWSUVDVV": null, + "C636AVNC5C5EKILXT2AQPXYLSNH7LCAJKVDHP67MVHULFSQN": null, + "OXTDOQG2VIEVYFC23SKOBSSPGE55AVZZADK6PIHP3APVPHND": null, + "JLQVKV4Q2BQHK355NQXZVX4WJBPFOWSD7WIJX2P433KYO4SO": null, + "E4XHPOPWH3PRCV5MGQHR3BCTKZMOK46OH4Q6STZDPF2FG6SD": null, + "J5IP4A3DV3BHGGU3J72JVVTWNIQOLNC6GQES22MVATK5H7BZ": null, + "HHCCDMLNGOU2ABP57ION5TC33UF3NUHL2L3WUYCGZDWLDNTL": null, + "54Q67RURG4THOANPT3RAVF72TGKJE425GC5GD3EOKPY6MKVW": null, + "TG3BH3HBKFEXAUM5O67VVDTXZA6MHWSVNNLXLXIL2SE2ZEDO": null, + "Q5KJ25G2A4CWNGPPYXBZM6QVYA466MQX3HCUMUO5Z24D5JX3": null, + "QQZET7VFHGJROUQZSWSRDI5ADXVH26KEPDVL6PZ36ISHOKMQ": null, + "KWNJME4V365ZIC7SA7BYCVQUAG6URC2T6MHSO3OVDBJAUPFB": null, + "XHQYKGYVLE2PFNXQPD4OUWBASZO5OFVZISCVEFTU6K6KDKHS": null, + "Z4SPXMJIAMYD2H4U4F23FALBDZP6NRLUBDFU4PRGZ4SXGTI2": null, + "HSCK3PEXH3I3XMMEMIHTM7SDJD3GOKXUMCGOL6UXJXLCSCGN": null, + "BIUYMIDY4EVGRLZ6OLJK2CE2FS5TTELIWSEA6UHKUDUYX5LM": null, + "IJJDLN5ANXTMX54P6GW2J2EJGGWG257YEAOZMXUSWK7D76LH": null, + "CLMTO3VSAOBAOBSA5IGOO4W7KEMLOFUOIR564IBKMJA7RWEY": null, + "JU5DNSHLUW34DT3IQ36JBV6M7EPILLMBALURDAB2KJXF6HQB": null, + "VXZXWLNQZFJPNQVPTOFWUPLORZD2XRAFXRVRNLUYTPBO22U5": null, + "HNACM55ZSGJ2FGRMOTXLVVLA32BC333QGC4HFCDSZ335YA4N": null, + "6J5GIOVKU4PKHHU35DWL3D7GTJFF75FF4FKSP2HPGJ7SQ2DP": null, + "O3NJM537IQSKKWM3K7EOQSNQDTR6XKUA7ZR7CWYHYYLHKH63": null, + "B4QMXK2EAR5E7KGHLODCP56DX5HW7IQVXWHFFCZ4SPSSNGJK": null, + "A5AUZBXKF67OXO34ZSEGVXI5PAIG6W2VG3U5C2Q72SNWYNEI": null, + "ZGDQ2AA2IFBSU3APKAFL5AO4C4DXY2YBEHXE5UPPVCTFZ36K": null, + "N3XZ5FYZEO3ZX37OMUJX3PIWEEV7TVEXX64KKEZEJICKXMTB": null, + "3EVOEEWTD7OABLQJIJYLOSVHBS4SB6QGX7GPDFGWI2DGAWKR": null, + "HNAEL3D7E2S7IYLKLIK4CGI56DRGAXA5S6KG3RX75PMJ6BVI": null, + "VGVW32CIRX3M45J2CPCUPPHNRGNG55MKAU7YF3CDNMGONW2T": null, + "QV5MW2W6WQSHNC6OYMWJAWEQM7LHXRMGWCJ7RI5WQ3JGHARW": null, + "IND2PUTLFWXTEUY4MMEXCFJA7JN7DODE5HVWC5CL5ED5IEUB": null, + "W2IA75XHJRBRKXLHGB7LXD7ECYEZI4V5N5I37UFXJMFWQMYR": null, + "AWTZO6OG6TCOUVYYJCWVP2JYEXRXZ7S7F7QKUKZS7JLPKN3H": null, + "TCARJATK42Y66SPMGOZ2LHLT2ZPZW7MHGXL5IVTS272FJV4U": null, + "XVHBOY5WQDOTWXVFZYQKZ6GNRWMITJDDLXSJ2T3UWF6PFOHL": null, + "CY5FGDYLB4UFR4AJRGLGPQT3W3OERGCXC4JHYKJ4HKSFTGK6": null, + "B3SJGD67GKIEAOZISX7HWENPDBYJHNJ47JCREGXQ6G2RXPUZ": null, + "LWVJYH7M5KXMLPFAHTMF6FKT3PSIW2GRC37AHF65PQY7OUE4": null, + "UUFKWC2DOV4ZQHPDPQPRCBEYNAX6OFZ7ZVJNYGW5YZCMSQIS": null, + "K5EC26CUN365DZ3LE2NHOINGZHXQ752A3VTPN5IMSRYSTOMT": null, + "22RV6RSSZIAFXOZIRAWJAIMMVHYWGL2TY42U3TG2SPFN3I6P": null, + "Q7VEOUC52OLXL53CR4XQSGGR5QZ2QXZTRCBACHQFP2HKN4SZ": null, + "OZ2ZBCTBC32VOHHBDABY2U462OHUEUS724RUS7Z6TW5K5ZFQ": null, + "EYXYWTX2UYI6MUK5L65WSTX2FDOJASIMG6ER22NLABNGAEMI": null, + "U4FJU7RQMXXDMHG7B5WFLXCZBNE5PMV43CE5X4RJSJUABT3U": null, + "K3T56AL7IXTAGTVIWZHYRKVPHLLD7UVHV4UNU76F764VGY75": null, + "U2BRKWY2RBYV5S3XVZTUZXT55CXMB45KDMNFMVY6LENW2DH5": null, + "YKLPZ7SDAG2O6NSJFLVGFVCYMY4WZKXQGHH7OO2BKGGVLQNP": null, + "WSC2BHA7H6Q62HJIIGQFX2OU64QX4AEU2RZQVIC7LSIO2JSJ": null, + "QIFNFKPJJCYPITMAYDAOEXBVEDAKBBR3DV5ZB7DAVBIAWI5K": null, + "NMBGIDIK3BMS5ZPZS6ATTID5BOAXZAH2VUED52JSC5XGI42P": null, + "LTSG7BGZVBLLXM5U2QDW5LNNPM3B5EQZPHES7JXU2EAQG266": null, + "5MZMVLLM7YHR4PTQCGDGWFQQLNN532WMTFGX5CFTDURBYEOH": null, + "UOMT2ERDBVXC3LRYKCVVUNROBWPGFHFWKFCW65HAPXN2H4FD": null, + "RFYZPAIVYHTITTR5AKOBAMYKOA3VSKRTK4P4ZOS7JFSVEY53": null, + "QQJGQV6BSW6PL4DZGQDWWVTF7U5MEVPQABOA4IRP7NOD4V4V": null, + "EFOSJBHVPSGTB3O374JFJW6MVW47ODOZQNKYSWHR5W6UZECP": null, + "YTL42MLIGIUD6Q3AMVMJ6ZMWNSXSUWCKV4ZUQWSGTEOATQC4": null, + "F5IL5OV3Y6E4QEE7JMQTKV6ULJ5AQQKQPZ23VXK72AV2P7XG": null, + "AZEV37T65EWVWQJSISCHTYHLWRXWCR6XD4LJ4KFLJ6RAOPF5": null, + "T5TAAFPNZLVDYHSNNHIJW4KBZWNFT5CMIPIWW3EFKPU4REYG": null, + "W326OLSKXRLU6MEIVUTKFFHFGXEH3VM43F353L3NHQP6HE2Q": null, + "MIIUZQ4KGTLA66VIE7WPN4T43SR6Q42YUKWEP6467AYWKU62": null, + "AXSJHLTL4FXCMLLJTQS4HIBRGUY6ATR3GZPV4MGXLWNFHDYU": null, + "MC2CMWSKD2HMTVIWCMSPZWHEGW73RWEZKU3IFZJM33IW3VI6": null, + "ZGOZHC22WZN6LSY3KK4HK6RF6F73VWSB7U47KZSLTYOQZAVH": null, + "HU26VJYM5YNEXCOCWCVEQNNZ2WAPFEVYK67JZOHMSZIOUWJN": null, + "6ZA46O27SWCAX5MQUHZYFV5UNQUDLZG4LDA6VILK6YRQMMZ5": null, + "LMGGW3CAN4T6DSVJZB46LOBI6KTZN7CKHNZ6BMWRBL5PVYXX": null, + "RZKIP3F5SY2P4NWANAQZJHPH34CU3GMQ4VCN4QXMP7ZBSQ43": null, + "CMUAX53FME5Y62VC7T7ZOUZMOPHBDFVLMVVMHYDDBZEHMOOA": null, + "ORTA47K5MLIHEUXQTFFTQNW2RMYQSTVDJXUNIF334SAJJYMC": null, + "XEGLAWIOOPE25FDXHN65P4FYJVB46M4NGGXFAWZ5VDWBBMU4": null, + "WZGXOCCN6GENKYYAYCH6UQD45BIPSYMQOZYAYRU3S2JNJLU3": null, + "MXDDSZA6VTTYU56ONDE4QZMB3L2D7A5SCRCIVBYYVIKFDFLU": null, + "JJMW475CTRXRR4R3GEZ77STHMKHTQZYFZHFUFXEB77SV2W3H": null, + "J3TNJVNF7QSTIJDEEZMLTQECNOES4PXQALSR5ZPYDTIVVKUB": null, + "Q5EHPI6GHPPZBATKHYYEXNDSYMW6QVAVKKHC2XO7RU7XXKQ3": null, + "B6WGKJEZH7XBZ4VFFRCBFYKC2Z2ZQXMY2HJQUH4LVI3EDMMU": null, + "NZ737IT3LUIMH56R66WFETEHFDOZSNVPTHMQTW3JHVTN562C": null, + "B52PWLRNPFN73AA63O6JFLEYSPFQEIHQ6AI6YC7KWOYFE5OW": null, + "7UTTRFE2I5WB2XZA37L6F7RWCII6S6HLXZRTLSJYFOENAYPI": null, + "TJJDGG7R4RNVAOXWRZRZB5K7W2Y6XB7LUYBDOY6H5IDRM3ML": null, + "TOG35JU7ULNRY3DE2XYDZ25WZETRSO5WSFFYSZT5IIALO3ZP": null, + "2QZKK4CMZNIKUWZZB22ASDR2BYNRAMTNS7MVLBA7Z7RDKZDV": null, + "US4C6FXHKR4GCRU6IJQHSAJXLNQGUDCDEPEQDU5C5D76I6XX": null, + "QOPUXM3ZKXTPVGMVVDMUZZ75KH2S7DKYXSFCQ3R5RYO5WP2J": null, + "GZ2T37SKRE3ZX7FARFWWF3WG443LVP5X6ENDLDHO7GBWYHHM": null, + "VSOOUSBMGIPEVAPYAGWZOLDUW5HSTRMTBRTUYLQNHKVUBLJ7": null, + "45HJFJQ3YKDBFDZPNDO46YT7DLG754XZWMGJQ7YPJXQ4G4N4": null, + "4KY77KV2OWWFEVIBSUZRGZF2V47BEFFHIHNMAQVK65E34ZF3": null, + "NB334WI2DNPLWHGXBNHSU4436ZYDQ4D2S3JMLDOM35QINZTR": null, + "7K23M4FJGIQFWUMPRDZIK32MF7HZULYYSS5Z7N7QTEJGET3D": null, + "ZBMNFKSEG2PXKJZIXIK2MHJQ2ONRJUJVCDBOCHNERPGMN2NQ": null, + "YMCOX2NMBDL4J6Z7JBEWHFSCWON4ZSBSBU2WONEYYOYRA75K": null, + "GDOVKPAWZFHLAPQ5YHCFWL4NAMC5G2DDXFWUTR27XQ7LEOOQ": null, + "CYBYK7ESXTUUHYQVPMDI7VWAZO5TVGLIB3GB7NYRYVDLMYKG": null, + "4IYLX3IDNUJ2DWT4RM3QJ3IMVE22X67EW5KWSMZHIU4W2W5B": null, + "EBWXJZ3PX7LE4JNB2XWJJNXL5QBVSJQSXAUJMJ34YJKR3JJU": null, + "LEKOXMXHU57JTRZUKMCW4WDCAKEOXPHJ34ULXN5P6DIEOYLL": null, + "BESPMR4LBE3G4MTWR22CVBYH6NW43HO4ILTSV3P543JZUBD7": null, + "5SYIBXIHGJGE4WHL2HYUNK3X4JUGOJOUMKVJMMXSQDKJZHFJ": null, + "XN42HP3QOV34GMJA5VINVW3O7KWW2GV7VDKAZDFBCC6SSHNQ": null, + "326BDEDWGYW3IMEHP63I6LVGSRMS6DUUNMPY3YVWXCH3YA67": null, + "FYNTVFBPC37FYGOXFIXJP57FNX5MYDGUWIMUYMFOJSOXRRDS": null, + "7DRCBIQP4EXAVNEMWOZHAEZ2W2EIMKD77PH6JJWP2BDN6NFN": null, + "7Z7LWVFB2Z26EVYZPLQAOQ7LXLADTHUA7QGKDRFLXRQ3ZJUX": null, + "EOZ2S4T75U62LD4QUZNTOHP7SNVJUNNSE7WWGHCMC75O4XPW": null, + "TVG4ZY3YVNQV7WPZ2CEW26QTGWUBVJV7FTRF4TE54446J5SI": null, + "MQ62OHPXMGGASRXKOH5MEVGLYHKNWBT3DC7XSXPXFHFXFO5C": null, + "MBRTEJLOZ6U43EOO2IS3AHNDCT7WUEK4XN5ZRMTPBKUFXUWU": null, + "24WJGDPNT4E7SQT2IBSTHJGYBMEBKS7VPGJYBRRAT5YXNBC4": null, + "3KD7I6FOTRB4U2JBT7CIJOPD5XHFWHESYJJQTQVUQ3IGIPVZ": null, + "25XHQ7A3DWKVDBX2ZFNIHKOGJCXY73N4Q6PUBEWGH2I55XVP": null, + "GE3YTUBPOT5CFJU2LQVMZVC67NFNLXVWNTV4ERN6BHVGCGYL": null, + "VXE2WHW6UWRE4WYTAVFAQ75IBYUPNZVMHJC44DGDPIAEOVVE": null, + "5JRWFOAEX5TNCAMYGF44C72EWF5NTXIRSVST5J3N6N5SLGFF": null, + "TYNIMWTDY2D565BJUNMFXTJHBUMWOTD4YSAFILKXPKX6FKRO": null, + "RDUDIY6N4RRUA6YEBBBFPBNYFZQUWRVURNYGJPEU6EHJA64H": null, + "MMRLX63PFJLWBJUTXCSLALIGK5YOHTLAY64WFQIYQJCX4QID": null, + "P4T7UPQNUAFMAJ3G4KBRHOQP5GCJP46XXYKPTTENUI36YQEP": null, + "VNAKVK3A4TN7WEZAJBJVMUVIKIUWCNH7B373DP7WAM7ZXYDD": null, + "VAPNA5BJL7OF7VRVSUEFAG6RZWENO5VOGMFVN6AB4A7H4VU3": null, + "TLVHDKN7326OHNXMBBJIVQW5FFFGPXSUR2IVTMPLOLPPJQW2": null, + "LD4OK3CY7MQGHUMQOMPAJY2NZUASJLSLWVSIIKIYYYAFYHIK": null, + "DXHC3XJCJJG2SMU4O2HDPMJHO4PNNYGIMLB5KSCQPNLBAJER": null, + "SANGKO55HOXMBC627JYHVBE3FH6KJL74ITOVF5GYODRRMEMP": null, + "TOQW7HYYWSFH3NKL7SITPX5H4HLAH7BKL35ECCAILLJ5B4TA": null, + "WUKAWAQHSBKAUAYEQ4UA5PKFB4676VQNQFLXUIX6UCDFZ472": null, + "BDU5VYNLNHR6HOLMZI4XSDERPTMVJ4LBUX5XP6W2BQWH3NLR": null, + "R6BT3RGKODHZN2AEX26XHNSLCHGPGMQ7IS2ONRTZEPJECW7A": null, + "E7Z4FLW3UW2ALRLPSMHQWJWBK7VWS63H3AUZZL6LHCIG3Q5B": null, + "FUZAITDO5EH4BU3ZAN55R2RQZ75LRAYI4X3MEJKJD44VHOT7": null, + "7SZ7VZ5O2OFPJL3K5JJKH3C2ZYAJCWW5GYXSLVFHRRATZDFA": null, + "6H7VKVPSP4MHB6P7H5KLQQN3Q6ZSS65OMK6GJ3JIUMHQINMC": null, + "QNCN75MNVAVH2OQR3JE53SGCKLXPSB2XBTZ55J3AX37AV5HT": null, + "JCSYRKMHDGVUVZO65VQVAV5SGQS5IRS4UGFNFKMYP6CXMHXN": null, + "JXX5VCQU2Q73TK5ICSFX3QIGA6E4IFRTGKPZZY32UTB2RY2Z": null, + "BMUAPYFGRJO7ZQAMMSSEADU2RC3LPAAXTORXLSIUCXCSSC2P": null, + "3SPFCAR2V2PQA3RWOY5ZZXI2V6UEUCZWL6SNCGEAGNR2JQZV": null, + "KUW7Z4ZHRUX6DI6Y3ME7A33SXUAQPXFAHRG4IEU32ETMGTLC": null, + "64F67UZGQHZUXLN6HCATAAX2FUQNK2WVOEJGBQ27H5DVZFC3": null, + "GHMJSW2TE6E3JLFDD7T6FI67HBDHNDVLGEKATAO5G33TID57": null, + "6BZEOJR372ZLNXUMEQQUKHHDCAOE5W4YDT3VWGI3YYPYDC5R": null, + "62JOKD5O25I7DBDFMM2BRQP4HI2VJTUHMEF3G3C7JFJF2VNL": null, + "NEF5ANHSBNEXLOP7FFH7ZVHPDOCHQQ6EYOG64JDZNIHBT44L": null, + "ZKLJACJIQT6M7KUY3VWTMQ4WD7RETAWN7LDUB7UQA3NZHZLC": null, + "VBZVHDFHE464JTYWCLYNAA65RDMVURJHVZHWRL3IKTNT6AH6": null, + "FHBYZO5SUBQ56J72DWYOUZSDKXE3SKDRWBEGLQPHWUGVSW5B": null, + "HHWRIAY52UXIOIKQOL3PBERZFDCQXAAUIDT4RTZF2VETEY3Q": null, + "JALKMRCQEIXX3JPLOACUZ2DKA5I2RWSSSIYDVSURW475XHR7": null, + "IMQUFG6JBGWA7R3D3NRMJNOF5MKE2NU4H2LAI6UPIHUEY2ZD": null, + "GWSUUFLKG23Z4BXTLB2HJHYVRWAWHKV5MA5RVOEE77Z65ILK": null, + "ILKEEWZSHVZSQ5M5VAZH6MJPBVQVV63SCQSX73YGTOQZBFKB": null, + "TBU3SS7AG7QISWIK2KKNE77ISJUEVH3ZV7QZJAEHLMAOUCEZ": null, + "EPN2PRVPXZGZ6WRX5ZMG6UPIM2V2NEA4BBC7ZDAIVCEKMHR5": null, + "Z7GJAUSWDAH2JUMVX6IZB2PRSIUHYUKXGKJDM7FXVFDJNDUU": null, + "APOEQP3DLJGKFU7424CJJBFDTWODGF45H7HSXT3GO2UC3VCI": null, + "LCYBWI4HYCSVGBSWWDJYDCWQZGJP2KVSXUUJBO3XFUWOS4SA": null, + "KOTWM653HSOQ2JHNAZGZZA5FGBBJCCBYPDVDE7WDXXIHTULF": null, + "TIPJO4GHBUJQKWKVHK5RF2NI5Z6FAIEBGFPR5L4SSCLS6IE6": null, + "QJZMGE4B6UPJ35KTTNIAHWTFV7DFQZ2QMF6DLHB2AHZQ45CD": null, + "SDV2RDMAXCYWHJJRPTEIZVE6SJST7KQJB57AXCWFVO54E2GX": null, + "4NW6WJDWXCXG2TS24H4I7WF2IGROPO4UBN2HJ64M3CWBU2M7": null, + "GJPMFWNBHZ63VB5XWIM52UO22ANEXDYLHTF24LGBC7XXI4SH": null, + "I3TPFLVZ47TOOMM2G35JFQAYHLAIU3OXV4SXZEP67DNGYXN3": null, + "QMPKHHYWWSV32R2LHCWFKBFDXUDUXTZ7FRZK3TCF25CSFNWD": null, + "J3C6XZSMIXH2SQMBUEVWEI6UZVX2GJZCAYSPD74BBUUK45RS": null, + "WHK5HZ42VH6IJ4U4EUKKVLRAID2FH2YISR7IV6FMNHQPPSH7": null, + "C62NUQB2FUJTY5VRNI6ND26FXCUVACSUTTR6NZMNQPYK6357": null, + "2JXXJE7WN7QWO6X3ESQCSDDBTZXOY43L5AODQUIR5P6Y4PZB": null, + "FQVJ4Y4GES3RGRABQCJIDIYEUNTIGETQ5EOXW25SZSYNJENT": null, + "IH2YJNGRU5Y3ODZHMWNV3TIU2MGCNLIPV75QL3JL4I7PH5ZI": null, + "RYUBMVYE4PL6JJOSBM57NE2RFKCY2EB3EQR3QU45MJHEX5IN": null, + "KRVCQJ6VSHM52MLDNS65PKDYHNBJAHCONQCNLXBD76LDCOFY": null, + "W7MB2FYKYWXDXNOKVWJW7TSUANZIGE25NABNIAK7VLPLKQQH": null, + "QUJNQSAHDXMNHKHHIRBEFONX6NRV4NA7NKFRDI72ZKVZXR32": null, + "SRQAJHTEQYVNHCJDTYHA72VSYS4FPTHXGPFYP6CQRTEUIWVN": null, + "GYQMORZKT4JGWGOD4KBEMUB3XZNUM7H4G5IRA6SYDZOGAPVF": null, + "73P37OKSAJ5SWM5NJ2QWCTKPTFNLORRRGBNJWR7BTCRLKNCO": null, + "D7YVGR63MRZ5YS3UTCUZ7REPWGB6EMGNI3LXZUDAYBSZVGHZ": null, + "JNUZON5EE4CF5UIPXIAU5HKQSBN6O2C3OXJ5IT6HPZMUBXRK": null, + "3UMKRHCWRV2WNUWPF4WKESLI6EOHPFC6FOXF2MGP6E7GPKF7": null, + "ZPWCDBHEOCZRBAVIQNGRQ4WNKSE4XCXWH3PQSBJWVTMLP6AD": null, + "RCOP6UXD6CG5XYUXFXT7HDAWQA2LRA52R2NVABFBB574N62D": null, + "6EHQW3VGWSY5MQKBQ4PWU2YD4KKXPBUFJCBEEY6GKOGGGT4P": null, + "V72EUDLMYSS47DCO7XIEYQO4S6KK7ME4C6VN6IWLZALPDIR2": null, + "EX6JHHNN4R7BQVBTVXYRD54J6BLOJTRHM64QBK3DHUWW37KF": null, + "6GGFMOEZN5PBE67AJM6XJKDL7V6X26X3TH2WVOO4X2MEQJKO": null, + "LYM2NDKVFTJ2IJV2G5HTDDXFDAAHVHVMVTNGBAOABW4JLB7V": null, + "5GPR3EHGCAFLKH4CTOZK3JBHCJSEEFD2Y5GS5Y3B5FPXAK6H": null, + "3TVZ6BP47YPHI4HKRIK43AJPRVM5UO736FF7WEXI6FJMTKY7": null, + "XDL7LZWG4CIO574WINYHCXMGRRZV5BMZQH6GPTTVPBWGV4MD": null, + "OHDX42IVKOGGQVXFE7Q3DKX2HNXGIZRAZ5TVVKQ34BO7UKPB": null, + "QHSOVA5SCRL5AK65IALQZWLHPSMLOOHHS6JN3LHDCN7DEHJ7": null, + "EI2J32TUZKPKSWOYH7EPPKHISCJ5SPTUFJXENKZJFAPEFQJL": null, + "3FFPGZBSH57RTBR326VUSL4G3DELAIPWCCHB77LFG5CBS2YU": null, + "VOLJPHGJOQKGKQ3PQGRLYJBZCIF3T355GXCQQKV34USNOXNX": null, + "ZASYP4G3K3DX6MMU2CK2P6GJ2PKRQFQGFVEZGTMIRAZBDMOC": null, + "MSLOXTCY6MPU6XRGIJ7ZGFBB5J4RTGTEC2UW2LO5MIKPXFJO": null, + "DM3ZAC4JV4IDN7ZZ2OLHAUCUEWYTMLZSQQEARJF4JVBUTE2D": null, + "KWIXQOXXGHTUPBDCHXV6ET4YZXIDCYZEQTFIRHD7DTMSGZ3X": null, + "SOF4BRIWEU5XLSXVFE6IHVVDYG73RK5HJACKPUNFRNEDHRWS": null, + "4FECMJE2AGQGN54LFXTIQFZC6ZVJN3LY62YCS4E65PMW2K5J": null, + "VDCWL2B5OEDDB2YGM7Y23WLJPJBFESITFU5AWDPUKDUMFPBO": null, + "W6VC6MV4GBWJ7IDAX4DQHWJSBUJHJN7ADFJ53NBVND3TXUCZ": null, + "Z3TTBMVW3FCTJPLHXITOVK4LPLUFJJY3CIYKJ4QY2DANJ53R": null, + "O6N3PZGXI5B6NBTOFPB5WWIRJ66O4FYLSGHDIJLVPT25YPWK": null, + "RXCNDGG7CDEMAOGCALTPXWLUL7A67D3JSKOZSZEQBLDW2F3S": null, + "XVKBWW7HRXDBW3YXSBMO7WVEUPVQ7LRZ44RVFI27PYZO3NTS": null, + "XUSRB4YQDOYJALL7CK2OYFPL7GKI6XOFYHP7HTW5H3PF333V": null, + "PCCHIGPV6SWW2O4YRPMFMNF5YVW6QY5IF7JPYAULF5WPTYKB": null, + "MHRU7JFEPHHUAULYL34RAEAGBU2ARZG63TGIIS7MHEQUKWPY": null, + "Y6EDYRAB7V6NAP57DRIKQ3SB57XBPN7MAWD7F3DM4DKWIAMA": null, + "JQXEFOTP5HPBTKL4VAXYCMJFZVGSAM3JVLFJPQ6KHVLCRXFI": null, + "U53PDNGH4IKMP4PW6AJV6K5Q43PYB6VUZ3IJVEKZK32IR5WJ": null, + "52CB2E7VQJ3JJ2SXPHQZZMER64TM2JQBSW3JMX7XITCNSWDT": null, + "3JLBHZFBPZQTO3MLCW6S5N3RIR42N6RGDHMP4U6IO6STOOVT": null, + "YTFVKDUY6LHHBY5JBBTT75RYI73Y2Y2DFT5PBMOLEVBJEN4Y": null, + "TAHMINQIUDTCEBCJ4UH2PUXO5TYMIIZTH4BX26S4NRMPFD6Q": null, + "4VJIQ6FLWV6ONBHRWDR34KXCTHL7HIXSQAF3FAKOMZ2C7QV7": null, + "IQWFFVGP6CPSAQWMKA3SWYOXAUL2YCD3EJYRQ56S3VXWAMUF": null, + "J2FABCRQ7HZFV4FKZKY2UOXRUO4FYXANTTWL27ANRYY6XZC2": null, + "G3TOY5CIOYIELRC2S35CGAS2E36TDLTO5XYXHFVKZNDFQC6F": null, + "SDKQB4B47LL6CAFDDYJWDS4X7COKTZOCQ6ELJBL2YF6RHZJC": null, + "L76D3LKKTUAWNPDXKTWE7JCFCRFVI4UX6NKQS3CAA2OWVF4K": null, + "QVYYK2GQF7DHSJACSOZPOQUCWWIYTRGEWMBIR5RRCV2EPQ5X": null, + "UM3PJVMZNDU2GJ6KVY5VQ2HPGMSJKVAQBDRKZKHBPBRCU5SO": null, + "RDIJQSPXHAUB7XSQQPOL3CNUR5AJAJEWAFYFSDO5G4QWZQCV": null, + "3CAVVDQOCSMOPC54JWKI5ITUIHAOV6SKAIIAAPAAJLBDTXEM": null, + "JHLSLTDSRVKDHWRGT55OZ5NC6YHGD35WHW4GPK77VZWPNVKN": null, + "6K266T5MHDGFA2XECSFBMTQDEE2C4S45S53XBODESR4ERZQ2": null, + "VJVWAFFKWR2KSTFIWGAKDUG5VQTO3BPTI7YFYZWZSBMMQOIN": null, + "LBSXWCQNCHYUG5M255T3W72NBPR5MBEPO7DFBCD277HSH4DU": null, + "WHJGXILLMK23VGXI2OY76SYJQOQHQOM6OSLT4BWU2KSD3OAD": null, + "DVNEV7ANOMDRQDHTEMD6CXCTO7NOY2MQQOLI47U4DDOJ2A2M": null, + "TV752NASHG7FG2JOGS5P6QLJ7E4W5NX7F3OYYRPOEFZ2NREE": null, + "S4DHHYVQ4RQ7HBAXW5ZKISZMULMLCFTSBFICXNLI2OD7YNF6": null, + "HSRHOS56TX6EEDHUZX7K4K6Y3R2UNHRINXWVK5WBWHDPE5HF": null, + "I67YQZJ4PXHFWHNHMK5SKUEFIL4EEP5B4BH3TJNHZPQOUXDM": null, + "5AJTMUDFBWW3EGM2TH2YAJYXIR6GKM7RPBYBRV6KEQPDDLM6": null, + "6V3SAQQC44I3CSDERRKA2533GYIWWHUZVR67JAWIBPJJBDBI": null, + "5I6EFWIWLDNJQAZNZN326TUHCUY5YOD4ITIT6NL7LWIK6RP4": null, + "NVT5LE35FIT6LKWBI5XZO2Q7CTQBFJ3IOIAFNXI7PGVHEE5W": null, + "E5I534XUV7GRNCMHBVFI7FMTSPYBGXKOFVXXSEQYYLVGCASL": null, + "3XDVU325YQTEXC7HFJKKKH7CTCCNNJZMV6VRT5GVED7HFKMZ": null, + "3UJYDR6QUVSSCRHJT6WWNEHC5OMYXOPL3EF26PU2A5HESFG5": null, + "UPRVTQXNXYCZG4JZIR7GZCCYTXR5VTUR2OKAJXEWGATCSIOH": null, + "2QLXXZPU57ZXMLJHEYDS6IHFLQHOKANOE5URI2TRNFNSIFUG": null, + "JFL3SN7LZ7M4RUZXRTYFQTUMYWYHO4P3ZKBGFDC2GGWZBPEA": null, + "SBLHOHHAOCNEVQI3UPBY5S4UKTTIH3DEJEDJHWMJ6VEWWTCL": null, + "TIE3GNWA2BE2WGFA7Y3KEHF4IF77M5XHZB3DIQLOE3GG4VQM": null, + "BB7XBWIYV33TZGTKHTBL4PDPH5ZQ6X7ZCMHS3KIQEJOLOXVH": null, + "6WO2JPOCRLCUSXS7BHNKFBDGFSEXCWYUFPK5SDZJTFJAEJRV": null, + "RCJUMHWKL3IBJ4ZVWHK4RCZ4RCVVTMG5ZO2KWZOIVZLJTSMT": null, + "YIXCNMIMZBA7NK2A5QOCLE77QFF6QDS7NGIHKMILIUB37EMH": null, + "ZSI25IY4L2U7CRPBLOYY5TCSAVG22XHHZFC7JZCRAVY46BWH": null, + "HUSGTJENHNIBJ7VSWZPOWFHHKKYH7H2YSP32LLQ2N7CWKRME": null, + "WTIJK6LZPBOCIJFBZEG26BETKTY5PJKQK5D3M5WVPWVSV7LN": null, + "ITSWONDXALFBD4WMGSMRKQXCVTL7JRKVFEHOAOODRQEFFSWC": null, + "IY3RQGYC2ME2TEUBYAQG5WJ7WOAJV5GTO6P3FKXWOLSJWGCD": null, + "MDSHVZ5WHCTCYB34ZABEUJJRXHQDKO5MSC5YVTGPMNJRXQK7": null, + "KHNSXQTOSCRSTX63S7OVO2LGMD7OVR6PZIGEKL5ZDYPCEKK6": null, + "LECVNJKLFT6P2HWX3H7ZC5DKJSSRZ7PWZVBN735K7I45SOX4": null, + "HFEO55KM3XH34UWCRYM5CFNQ6OFRAKM3U6TABNQDP74DT4JQ": null, + "QZOWC3TAAU67PVSBRJOOVZCBSRIOZCMLPB3FH4GS37WOSTEZ": null, + "TSB72AJ4HHOBEYK4CGFX3W4RW3SIECQYJMYISHTPPCGQNLFD": null, + "6AB4YKYVMU2PXRABAUBBBF4BJ3IOFKYWBJ2IMFMRVLCBI4S4": null, + "E3TI3V725PEP7U2CYZUUKJEBPAHOEI5SYCR3YZCMGD5EGYHF": null, + "APKJUBCO5NHY6QBYNA2ADB5TTPLCNZMHG7HGXXOLRBOZD46Y": null, + "QKL26OQG6L54OCKFPLMXI6M3EG2HI4EG34D7BNI5SBZG6OF7": null, + "W4KKIH4RPYXL4JZY24JWLHOATFNENBMSEQQ3DI7WW4PQIJQ3": null, + "4XJPWCDQXS6MSKI4EMFPENOX5FV7KMKKZ77LV6GJ6S7ZBVB2": null, + "LWMCTL5CEAVQDT5PEXFKRK7Q264CNVV6AU657OQ3SSPCDGSQ": null, + "CBMCT6STEYDOVXT6OW34OXGZBN2A77OGBPDRN5AZK4RXNEV5": null, + "OUGRMVL7PTQ3GJNWQ5WP7XXNYBIMVWKSNQ2QZH5RZRDEGUND": null, + "XKVAYVNQL7KW5EHGEWYRPSWDXNUEKP3YC3OXGEHKG7PGNZHL": null, + "ZLO6BOTXUEEW7UOENY2NVIFLSG37YPUETQBYYCQBJM5VXNG4": null, + "QMZJWAJYYE6WZQX3OKY34BPU7ZZN6ECDNIZOIXREE6AP3WJF": null, + "B5FU7VNVUSA3ODDEUDVTKE7GWPU3JQXWHRWYGLT6VFKSFYAA": null, + "HLHSAJUSHU5EY26UTR2UDJAM3BIHYYHF46MNLTQZJWDAUCDO": null, + "N73SLU2EDTPQ54MY5NWT7KPSVTO3TOGPO3DGX4HQYPZMFYJV": null, + "7B47MDGTJA3P2WX3KWLLESWTC7RJUSVUSBI42SATEYZVPL5K": null, + "YYLWTHMS5POBP3WVX5Q4NXQ77STWJTAHE6QK7GYMBIJU3TSX": null, + "JI7Q6GUWUTSJPHKUII5IVOUZ2QQ53EWNWCUM4PKECXWSVSEK": null, + "XR4W6GZYNYIDAFU7MWMIGFGF63OLKU4FWQZ4RAN3HWNXUINB": null, + "3KX2TVZZAQSYQHLDSWMVZVF4UAXYONTXXFWSGI6CJ56DXU6O": null, + "UR6JGWK36D4CU63DYI722UFUKLB2S52ZI4OAVZM7CVGGY3SW": null, + "VGQOGZH3H5IAFESOYWHOQGU5FHP4BJAUUK2B7AKDCJX3PUE5": null, + "Y5GO3VITRDTHWTMUULEA44BVX3GHVLIWFMTNUY2APWRL3JLD": null, + "F7U4AV4VU7YAEDK6SI64JJUNEHG2MEFLKNOI77IVDQS7BGJK": null, + "D77762UIMSS52GNAPWFCEEFPWGYLBPKWMBN75S3HCOI2SYCL": null, + "NNRBK2PM7FI7MVFBSUUCZVFTDOKXLNVK6I4MMUXU4AKDPTCK": null, + "YSGZXEZQRGZ3DSMNCNH6GSWGCRWQSIRD3IOR5E3XEUH5RORJ": null, + "P6KRZXZTESTNZHYLZFTDLZMIGIN5H74H2KYUTNRIC3JWCNJ2": null, + "QK36OWDC6RHQIASJXU2HZVIBARNIESSCWKICTRQ4B3OFUB6D": null, + "JQBWWRLDDMH3HACHKR7EKXFCAAR5E62DX3ALK22Y5AFA4JDZ": null, + "WWOLYDEZIQARIEC65MFSVB5RH3236B3E2YSGNEN2QY6A2G54": null, + "QT5UVU5QUPEY7VCTTW26JTO2FBUUBCRBYZORWGTYQZ2JZSCH": null, + "PJQFD75BGF35X4N33WD423KSDLIAWJNAZUBXQTUGHOW4PTXJ": null, + "A5VRG2DRN3CKKTP2DN5YNILXVCZRTKFXWILKWLZ6PNVKJTM5": null, + "TY4YPLWS4MDSKPG2HHIRSAWK37LFVB357RGGBRFP2P332HJL": null, + "SUC7ZGB6YKDYNAP6NTUZVEVNDL22KBCRZIGAWSOBUAL55LDE": null, + "Z5I7WKVA6754S4G7QWWXYTRZ3SGEG4B3KG5MLHP3GJDI3H7M": null, + "VLGCWOT665AT2R6EMOAVHNKVM2NKPSV4KI4CMNEUZ2YMI3UP": null, + "YJMQW3C2NIIZKTJY34XRL4HQ5A7EUMLMXTJFHHRE3NR3QGZF": null, + "TOEB56GVW7OQ7QLL25ZY3ABP4ZQS2ZZMIJRNTILE5CWA2IZB": null, + "5RGLCKE6D2MM5YH74OJBDHTOZIM7LN3EIYBLXVF4PGNBZON4": null, + "QMQPPFLB6NCEBYCQ5U2YWVYWRKZSFJLCDAAPYSPURDLXAU6G": null, + "UTAFBURT6XHHZV3Y5OZJBJJQT4342SSCOLWT35GZIJUPWTTM": null, + "XCIXTAB5SB5EMQLZW7GCBUS2N3XU44YELMLSYIFAJHHGP3VS": null, + "LWL5AM7Q4JPEDEORTLNDWUF5X4AIUI4QC5S4CWUXKXIWP6FP": null, + "M4RONO5HAPE25Q46SSRBVQLEXPCVQLKOKX2NYQWX2SNNGEVB": null, + "UVSHBLSXOHEF3AGG5PDTTDFVXNQPRHCNUTXYDEXJVXI7JCPL": null, + "C3PB24XOHCI52DU64XQL2V2OKZZYG5B4T6PUU44DZCH4DMSS": null, + "VGACAPDUB2J7KLW5PA474JQZWZ6QCDYYB2I32ZFYGXR64M2Y": null, + "NNDVFWEC2OE56D5PLJWEEVG25TMXCXISOUOYDOUEMUZRMZK4": null, + "57TIZBR3DXRX74YXCSJ2RXLZRXKX3K7H6WPS7DVONX7DOJY3": null, + "RFSCST6ITGG53EAZEBXD2VFQTJ53ATEOORQV6SQG5OSDR3FM": null, + "YLIXTKYNMODZNBM3L2EL435GD2LRJ5XAJBDZSYCU3OPZ4N4V": null, + "FBEPPECF3L4RB6QBQLGL44JDBCQCTQ5MOFYFCUQVNL4DCQYV": null, + "PAJST32KEXY6I2Y57OASSUFLF2BLPQQ7NZMVN6EVR7JS5LY3": null, + "76MHL43MEQWH6R552TULI3TLBOR22YDMJC5ZYQVWCNI4BWF2": null, + "A6KZM4OXBKW2NJ7X545F4LIDSC7LIAFYJ4CJSWW2BWSIRWUY": null, + "VND76C7TCKQT6R4X56OD4UYSOBZGC5BQ3LR6RXOX6LA3I5F6": null, + "CE2NODHXCRS4ML26HTI77Q57R7ZXKZO433LHHA66I5U3Y5GP": null, + "3DGAXWQDLZBPUYZPBGMRZG5DOBPTIHKAXFSCBLMEQHZ2A4W2": null, + "NAOTRV3ZNB2PK6RZJZ4UEQVF5M3YISGJNFZQQWPV2S5RL7XM": null, + "HLCSR65OBO7BJQPOA65Q6BRDVFPOL7FJII2LOANRJNUM2DDU": null, + "YCBI6X4JLTHKGAFR7XYKELWE7JW6VHLMFJIWF2ZC7BPCQFFR": null, + "QEF3LB5GFEMHAUDKPPNYGRKUUV6PAWU5XXYCFIHXI7PLGVGW": null, + "ABBQK5JKJZLMX4KGFODWSEHOPDTRHGDZCBO3ULBVOGUIAAGI": null, + "HZLWUQNBAZJSDZEB6IPXQIUMVWUPYVMVP2N72NJ4MOZFUKGT": null, + "7SQCYMGSMYW47TXUWC2J5674L4CRDIAO34D342D7IJ6OE23F": null, + "YAQCDYBXIOY3KZGFJCPS5VD7YQBPBFFFYEA4DPWFWJCWCJXA": null, + "HCZ7SSO422NW6O3ARCBUGNBCMUVEAHXMVKAJSDBHAQSFXIMV": null, + "DPX2FNJNMFQT34DLAOEIN4KMWJYLOEGV7U4VDH635AG6UA5T": null, + "QUO6FPOFFXUUKAZXYRN7N2MMT7IOJEG6NLFIH7B5JI5V2Y44": null, + "UJ6G5JMOINYVRLVISHWTGQDDDWA6X3QDFICKY4QQIHG3QMF4": null, + "ZR3VRUOZMQE4EMVT2WDB45TJ7KB5AGU5UBBPNL2A2D255MOL": null, + "2AFEUH4R6YAJZEODKJBMLDM4ANLCKRU2C33HFSVU2LLXZW5Y": null, + "3S4PV2VOBFB6GFRPG5SB3EHMZE5M7VAAFRJ3JQYHZEFTEKFX": null, + "6EFK4THSCBEG4LDSVE5N5FXSQJTYB5SQ7LKJRBL6IYIREWTN": null, + "HHYCWLKLIII7MJ4MYU7CJZ4YPOOUVWOKLXHZV5NT6LU7WWGX": null, + "XYRSXFI6XRY3YACAIVIZJAVKFTZPRH5FXD7E4P4LYUGX6I5U": null, + "6W72FMK5AP56TNCZ3LE5OTYZ3WYPARBB5AOXDVHGCBOTWZTO": null, + "7YNUW4DUCHUDJSSAWSYOYM2QXWTVSJWGDPIG2EAABTU4QLU5": null, + "HNVXP5XULHDT666ND2M3X2APGXOBCB7SCQB2D7MFQKKNVOS4": null, + "MLCMV4777C55OEVW3SFO4VHH56O7BSIDLZFYYTY3JXNN4DWG": null, + "MSNRSOCYC3HQCUXRLCBYFYQOMJFBDOSHJ3HYYYOHEPODETEE": null, + "BJB2U3W5ZF7WQVTL6R2F542WSS6FQDSVDMXNYWIC5PHED4HH": null, + "E26RFAVZYOV5WZ6WQDVINCGNG6ZYU2XCV4FPEKR45IASGARQ": null, + "4BK33GLSBFLRZHOHECAVVYT3LJHSQ5RFBSMKLMGTK4Z5RGZO": null, + "5I3526BP3QPLNDBEIPVQL2GOAMRBAYWOMILMQK5IT7RES3EV": null, + "IBHOZ4VNFYMLMUNOZIGK743IVASI3DXHCY2RH6SO4EKNGR4A": null, + "CCZT4EOMTISCMIVGMB2ZRUGFIR3R6WKU3ISSJ3VZVA6SBLFC": null, + "OGJUH7B3WKG3W2UFEBL63KLQGPSPRNIHUUKWTKQMBN5QG42E": null, + "Y6JCIA2AYVA3RDOUQFYWI4EMF64H5FIFNAHSKZ6LXCRXCFGW": null, + "VX3OCLLJZPGXWTLGERIMK5IS4OXKU65SMC4YS5JZND6VEPO7": null, + "UXWF26BRES53JKXYXEG5DWJXCR6USGPBWQBDJEVEBA2PPUAI": null, + "IB5SSNMYSFCNB4ODT5OQ2GAGPIVDWOBEI3P3EBWI7AUGC7BR": null, + "ASIAQKC3VSFJE7ZW472ZOAXX2T7JTCLZBN5BYEOAE7E67F5Z": null, + "BKQ3GY255BDDVZ52IIR5K3NFIEKV6GXBVTX3ROY3IN7XDAHA": null, + "JTV5ULWFJJOSFTX32FA6DJWADX5UL3NV4RZZS3Z64IPXDZNK": null, + "GSZ7MZXCFKAWFBXKRVYUDULPJEH3WSI2K634LAAA36M2FRF3": null, + "HSPTZMNCONTGJGIUWP7ZR277AYWTDIKPAWO4RODOIHQGEUF3": null, + "4ABCWRBBUAO5TVOSOZDF3KMCUCKIUCRJSBGH4WGKDHWH3LLN": null, + "K3BK4XFUTDJLS7KY4WJBS7RTZ65HY4N5NJ6AMKNKGO3K6DXG": null, + "S4VZEKYRNOXUITHJENCBKJN6CC6QV7Y4MIHQ6NLN24OJFMBP": null, + "MRM4HMHS2KAISLXU2XYFQCQH7XRVVC3EXSP6JU7FIM2DJHVV": null, + "QMNCR2JQYOST5MD3HI2I4MCTSJDFCAGUTEE6XKM2THC4WXI3": null, + "ANIF4DT5IA4IY7M5OISD4IW4J2TDVHHFIPEONUU4CV75LOFZ": null, + "TQHJIX3NKO5CMVRNOG4WP3YDSGPLTTCRBA3RDBPECWO6EN5U": null, + "6KI4L4RRXZ6WL3TRMCZLAA2W7AQRXDCC43O6AGYJ75NUEQO6": null, + "VL57QTQMHQOAX5MFQTX7GUWOECHVTLYJHIBRKMWIRF4QMN6M": null, + "JFTGBEP2LSZGDDFGV6IV2JAS3J3HB7BDRB6WEYHSC5EIFNA3": null, + "WLEZIN5PPCJE4W2LGEPW4N6AWQ4RLE2AOGFBTETY5HNRSZCY": null, + "LUJRHNRDNK7YOKST7KRVQGVE2ERU3LUVPZLC5YYLCUAX2EEU": null, + "F2OOXAP3FFVMQMJP5IVDLRVV6IP2NUTGT5MGZCJMR2IFNA55": null, + "SVL525L4TVBTLMH22DTXVCNECAZVUTMMYDTA3UQGV7U6P3YU": null, + "546BD77L33PUPQ7TW3GJJVVJTYKHIIKF7YOO4SSGIIIOIJ2Z": null, + "FCZRNOURTDJI2BE7HJ3P4MMY4WYAPFFBCTVFXVTYSK4UB4JK": null, + "S2U5XQEC7I4HOUUR6HFXUF2PR2CLNF5UEIPJHTNF2JM5BZUJ": null, + "JTQGSOTIPVYKGYJBUQC3Y44RWE372S7MPMFDETMH6OEGUJWA": null, + "W3DTWDN6YOEPVUJVUDNPWCLQMXXCLXQPVYU27675LZM4ONDF": null, + "LJ7P7AJNNHJE24PNWQDK7J4VGGNZKKR3OPVRFV5A4U6LRFRW": null, + "I4QO3SZC4455G5PQIJPUUNI4A2BPJKTH5MBA7LN3HRIW6EFZ": null, + "NNR3EXDDDPBTOKTRBPR5SO4OFPXU376ZIEHA6YHEJK57ZRGH": null, + "4MBIV5HD4ZMXY5NIKZQIFKFO7S642PC7CWVX7ATXAXWQWNGU": null, + "A6S5KTN66UWYBWG5CZXJVCJ2F2EA22BCZDFQMM523DU7VFBG": null, + "AOAPML4IEVJZSZUOONTTDYSEN465IHW7MZXHSQ55E47TJ2NW": null, + "ZIW5DXTPGQLTTRHPRQB7SADQPCSTXQRMKHZIXA6T6YW2BMRS": null, + "OUHF6P7JPB5Z2C2E5MEPNQ5R3NY56KNQFHG3RYGWXBYKRRI7": null, + "M3JXOC3CTIEMVHTQW7HB2WQ7L7Q54AWFY6F2UBTSZMDXHTDI": null, + "WQQA7JW5NTSAI73WVQMMAJ4IO6OKZR32GTQTMUWE2HLC7DRH": null, + "WGDVRLD5YWTXFOFTGBBEFCG455EK3BZCZEE2POAX56O3EOQW": null, + "6KAR3LTBYTJ6WRGOUQ2TEPZKWVVBPGCO4OVAN2ADNDNLTOSM": null, + "VEWL2DORBATRWF5HJ7LG66NYWMXH37JJU6XWVGJNDVL3OSAM": null, + "B4HXCGMG5S3VEOZR5IUYOZAEFL6WPRLXB26SLWZHRY3WL3ZU": null, + "REKI5EIO6TNXBWJIENJDQ5CAYEYZC2GXVPAOIWGVXKN2K3OE": null, + "RBOY2SVFDRIKJZWTWVEGSJLHGIMAZXIF5HNBZAKPVRTEFR3A": null, + "SIOSHIHS52CHIB73RFONJOM2HJBTRLGGDFW6JAWTR6UPJBVB": null, + "ZGHKTW43CXC3CBOLSENIMDQUIR22VNXSE6HFBT6ZUA3TPODL": null, + "XA576OGJNZK3AXE3FJLSSGN5MGRK4FJJ2XX3UHHFI6NO7P25": null, + "22VL7B7ZI53VMYEYHKBI7XYNKRQW634B6RLBRXRJN4CQJA6G": null, + "YVHEMU6OLF3FI2MTMZ25QKT5F2OUO3H6CX4WRNEXVH4BO3WZ": null, + "3VJOBPUJI5DUFHNRM456UWSAHIZYXICY7ZFYMECCUHDTG444": null, + "BXLYOEBYW7R4MWPNTOZ2ZJPDDXBHV7JMH75NCD26VGS2VRH7": null, + "GCZOZTTLMHTAKVUQ4TSDOOPHEGK6PH4JQ3ULKZCUIEDW2HLX": null, + "TE6B4JOPAY2CEQ46KJV7N6MY7OAI4VA3UBBXGPOELN7KY5T7": null, + "62BPAKDHZ7ZRJOMVZ2SX2WAKFQATUQLKDQ7YGACJPL2NP4UR": null, + "6U3MTBST24MIPS3HSZJPTBSZJ54T63GMZGZQPGFBS7JGBUVX": null, + "SXBYC5BKXYT4DFNVSS4OVRYLNA5JY4TXMVTIFSCRT6Q5C265": null, + "TAMMZOCU5GDDOIRG6U53NW3UUEUGI3QWW6YY6GWNE7WIHRNE": null, + "O37BSKPNGDUUN24XFSCR2IQHWFYUZJBPWSNC4L43MH5HV272": null, + "AZFWV3I3DANXV3HJB66QMCFJ3UTVJGS3R3IP7VROF2D5JF6U": null, + "W2BLY5MU4PA7HSENYW4MO6VHHPBXUFCFMSBWTCL5F3BIPBFT": null, + "ILFL3JG2XQGZCFBJHZFQRZMLGHZWVRBX3M5Z3HXW2A4GDMNK": null, + "O7VDC3EDG5I567RK5BKXMKA2R6XPHQQPDXQTCZP7BHKV5BK6": null, + "5ZMIJOTL3NPRKBEPS7542ICCNHHUJ2BNOZ7LSL2ICTCUFGSC": null, + "FCTKLPX7PYRSVVBH4KN46HEYLJEYSRTQ3PCUU5RY3BROUZKU": null, + "7EAMJ4C7NUA3XMDDOF3YRJA7Q2BFXFCI4J24ZXSVE7REBRFU": null, + "NOQ6OL6G7QD4ILQ3FAEMEMROBCK4OK3LX3CRMHMA6GG5YIYK": null, + "N3XXFRDRYPWGZ3LDGLIXGLLJYKEHPW4565BUUL67OLMXP554": null, + "GFHEEY3HHESZDI2YHTDDCBKGE3ZPWPXW2WE5AKNL2Y2TJCNJ": null, + "JTUQIEPPBM2QC6XBY3KP2NSDM6WUCJMORCBXNU6ZPXPOHEIW": null, + "V5VTVJ36JZDDO5FIOEZNAKYWPRQSUSTEZAKARDOHQEIFLACE": null, + "KUTOUNOS2QL4O6HF266ANCBNYUSIT66TANXCGYALCPZXULQH": null, + "CJILUW3VUBZCSO5DXTSE4HSVW5UJAJHHCSHGHADKCQE5OTBU": null, + "HD72YVUCR4IY5MG3E73UM35ARFCUIHEPIMUSQXOKLVTT2V67": null, + "ELVTZXW3ZAKR76K6IV6ZHX7WTMKPKIFRPHIU3LK67WQR6IQG": null, + "NIZTNRLCIS4JDLMOTEAKPA6B2JOE76ZBQDEUUGXENEJBYJFV": null, + "FE743ELPJYDYWTJ374PZVE4TNGZPDZWSNUO5PATNYUYBDTBJ": null, + "FIT3JHSZMFJ7N2E7BL6PHEUUHSBHU55YBIH763TGSZQTIAZY": null, + "AP7SXAQ6HW373QPCHKKA4R7NFFUCD7CFB7EERZBNXRGM2Z7R": null, + "BAW6TALQRWXK2OWS2O2UV72BKZGBZCUPR6AXKFZ7WHZXZXWX": null, + "SM3FE7H4NI76AS5YCH6O34LTROZKJ7FEP4IKL33JUBI7FWZJ": null, + "BNO2EJXVMAPFDVF34NBTPSIYKI3UPFI5G2K6KGVU35TIHOQL": null, + "INHCLRC6WPTE2U7OQRSSRGCN4B5K4BUVSGFHEKG5DWJWICOF": null, + "OEHWM7QZ3H67QC4ZQY2USKQA62NLMESA543KWPBUKV7N65TQ": null, + "BN3U5KDJP3QGOSBX3TH5R2DR6PZA5Z7BEGVG6MYRW5GWUCGT": null, + "ID7S7JEGBCI7ES3ZN7PIW5NEP67WTL5H5IB6WVRYS47EEEJ2": null, + "BG4MHZNCCLZQN563CZ2D72CPT5TASZZ6N6L4JOW2XPR7GIDQ": null, + "IAQKAEEUCCT3ZZY5LCO4AZW6F6ZNGUAF56UCD43OPOKSMBHR": null, + "LFCSYYMAFZ5IAB5O4QIEN5GERYIGTH4JH266LORQ36SB2A26": null, + "J7W62H5B42N3YUEFS5F2MECESYBUVHXSIGRMZL6ZNQMCYQMQ": null, + "J24FG5J3MUQOCDAVVCHM6BJWZW4Y7VCSC73DW32TMKIUOXPB": null, + "DGJE6OPBSV3JW45P5WC3EGUMIETVT7MIZX4EA5SCY2F3JKFL": null, + "KWTJYJJT2LMBHE6WH4LNJEHNMNJVOEQ7SLLXGJKWPGOFDYHQ": null, + "7XZDDO3CCV34UECRKEM344EDKKUFD6YDUJ7EW4OAETABTYWV": null, + "BPS2OSY2SOAFFPRY24IEXGZVBEUNVIWZYTVVZRUWT7XM727T": null, + "6GRVGHI3FMCQ5MQ4JR7ORANBXK6GMSI4XRQVE35LPH44XROO": null, + "MZHRR2BS6HII6JD3H32DPSYTTHCVXE4WSC7NUURU43Z5SD56": null, + "QJBSWHFQKABG4CALELT62JWLMW2JVZP35RDYHWHQPZYTIX5M": null, + "K2Y3YRBFB7F5PJJUFJDH5Z5NL2MYOQWGT5T5VI5SP7TVM5NW": null, + "QLONNH4NMZX5WLEJPQEWJECL5JTLTWDSK234NU5H55GA6PFG": null, + "NSSRUR3GI6B7NBK77ZQIIHOA4TEEA5UXVVMRWVLMRIP6SN3T": null, + "WB2TXRE7EPSBGACXUA4YE23M4WLMG3PVRMD2OOCIHNGQVDRY": null, + "3MDCQC5BPGFGGFDO4C4IY53NPTWZMRK5MWLJG2KX7OWVQNFO": null +} diff --git a/include/rapidjson/allocators.h b/include/rapidjson/allocators.h index cc67c8971..801558fd1 100644 --- a/include/rapidjson/allocators.h +++ b/include/rapidjson/allocators.h @@ -17,8 +17,18 @@ #include "rapidjson.h" +#include +#if RAPIDJSON_HAS_CXX11 +#include +#endif + RAPIDJSON_NAMESPACE_BEGIN +RAPIDJSON_DIAG_PUSH +#ifdef __GNUC__ +RAPIDJSON_DIAG_OFF(effc++) +#endif + /////////////////////////////////////////////////////////////////////////////// // Allocator @@ -64,6 +74,144 @@ concept Allocator { #define RAPIDJSON_ALLOCATOR_DEFAULT_CHUNK_CAPACITY (64 * 1024) #endif +template +class StdBaseAllocator { +public: + typedef ValueType value_type; + + typedef value_type* pointer; + typedef const value_type* const_pointer; + + typedef value_type& reference; + typedef const value_type& const_reference; + + typedef std::size_t size_type; + typedef std::ptrdiff_t difference_type; + + template + struct rebind { + typedef StdBaseAllocator other; + }; + + StdBaseAllocator(Allocator &allocator) RAPIDJSON_NOEXCEPT : + allocator_(&allocator) { + } + + StdBaseAllocator(const StdBaseAllocator& other) RAPIDJSON_NOEXCEPT : + allocator_(other.allocator_) { + } + + template + StdBaseAllocator(const StdBaseAllocator& other) RAPIDJSON_NOEXCEPT : + allocator_(other.allocator_) { + } + +#if RAPIDJSON_HAS_CXX11 + StdBaseAllocator(StdBaseAllocator&& other) RAPIDJSON_NOEXCEPT : + allocator_(other.allocator_) { + } + using propagate_on_container_move_assignment = std::true_type; + using is_always_equal = std::is_empty; +#endif + + size_type max_size() const RAPIDJSON_NOEXCEPT { + return static_cast(-1) / sizeof(value_type); + } + + pointer address(reference x) const RAPIDJSON_NOEXCEPT { + return &x; + } + const_pointer address(const_reference x) const RAPIDJSON_NOEXCEPT { + return &x; + } + + pointer allocate(size_type n = 1, const void* hint = 0) { + static_cast(hint); // unused + return Reallocate(NULL, 0, n); + } + + void deallocate(pointer p, size_type n = 1) { + static_cast(Reallocate(p, n, 0)); + } + template + void deallocate(OtherType* p, size_type n = 1) { + static_cast(Reallocate(p, n, 0)); + } + + void construct(pointer p, const_reference r) { + ::new(static_cast(p)) value_type(r); + } +#if RAPIDJSON_HAS_CXX11 + template + void construct(OtherType* p, Args&&... args) { + ::new(static_cast(p)) OtherType(std::forward(args)...); + } +#endif + + void destroy(pointer p) { + p->~value_type(); + } + template + void destroy(OtherType* p) { + p->~OtherType(); + } + + // Rapidjson's style + template + OtherType* Allocate(size_type n = 1) { + typename rebind::other a(*this); + return a.Reallocate(NULL, 0, n); + } + template + OtherType* Reallocate(OtherType* old, size_type old_n, size_type new_n) { + typename rebind::other a(*this); + return a.Reallocate(old, old_n, new_n); + } + pointer Reallocate(pointer old, size_type old_n, size_type new_n) { + RAPIDJSON_ASSERT(sizeof(value_type) == 1 || new_n <= max_size()); + return static_cast(allocator_->Realloc(old, old_n * sizeof(value_type), + new_n * sizeof(value_type))); + } + +#if RAPIDJSON_HAS_CXX11 + template + OtherType *New(Args&&... args) { + typename rebind::other a(*this); + return a.construct(a.allocate(1), std::forward(args)...); + } + template + void Delete(OtherType *p) { + if (!p) + return; + typename rebind::other a(*this); + a.destroy(p); + a.deallocate(p); + } +#endif + +private: + Allocator *allocator_; + + StdBaseAllocator() /* = delete */; + + // For OtherType::allocator_ + template + friend class StdBaseAllocator; + template + friend bool operator==(const StdBaseAllocator& a1, + const StdBaseAllocator& a2) RAPIDJSON_NOEXCEPT; +}; + +template +bool operator==(const StdBaseAllocator& a1, + const StdBaseAllocator& a2) RAPIDJSON_NOEXCEPT { + return a1.allocator_ == a2.allocator_; +} +template +bool operator!=(const StdBaseAllocator& a1, + const StdBaseAllocator& a2) RAPIDJSON_NOEXCEPT { + return !(a1 == a2); +} /////////////////////////////////////////////////////////////////////////////// // CrtAllocator @@ -72,9 +220,15 @@ concept Allocator { /*! This class is just wrapper for standard C library memory routines. \note implements Allocator concept */ -class CrtAllocator { +class CrtAllocator : public StdBaseAllocator { + typedef StdBaseAllocator StdBaseAllocatorType; public: static const bool kNeedFree = true; + + CrtAllocator() RAPIDJSON_NOEXCEPT : + StdBaseAllocatorType(*this) { + } + void* Malloc(size_t size) { if (size) // behavior of malloc(0) is implementation defined. return std::malloc(size); @@ -112,7 +266,8 @@ class CrtAllocator { \note implements Allocator concept */ template -class MemoryPoolAllocator { +class MemoryPoolAllocator : public StdBaseAllocator > { + typedef StdBaseAllocator > StdBaseAllocatorType; public: static const bool kNeedFree = false; //!< Tell users that no need to call Free() with this allocator. (concept Allocator) @@ -121,7 +276,9 @@ class MemoryPoolAllocator { \param baseAllocator The allocator for allocating memory chunks. */ MemoryPoolAllocator(size_t chunkSize = kDefaultChunkCapacity, BaseAllocator* baseAllocator = 0) : - chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(0), baseAllocator_(baseAllocator), ownBaseAllocator_(0) + StdBaseAllocatorType(*this), + chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(0), + baseAllocator_(baseAllocator), ownBaseAllocator_(0) { } @@ -136,7 +293,9 @@ class MemoryPoolAllocator { \param baseAllocator The allocator for allocating memory chunks. */ MemoryPoolAllocator(void *buffer, size_t size, size_t chunkSize = kDefaultChunkCapacity, BaseAllocator* baseAllocator = 0) : - chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(buffer), baseAllocator_(baseAllocator), ownBaseAllocator_(0) + StdBaseAllocatorType(*this), + chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(buffer), + baseAllocator_(baseAllocator), ownBaseAllocator_(0) { RAPIDJSON_ASSERT(buffer != 0); RAPIDJSON_ASSERT(size > sizeof(ChunkHeader)); @@ -279,6 +438,8 @@ class MemoryPoolAllocator { BaseAllocator* ownBaseAllocator_; //!< base allocator created by this object. }; +RAPIDJSON_DIAG_POP + RAPIDJSON_NAMESPACE_END #endif // RAPIDJSON_ENCODINGS_H_ diff --git a/include/rapidjson/document.h b/include/rapidjson/document.h index d1b90eb0b..b07e7da7f 100644 --- a/include/rapidjson/document.h +++ b/include/rapidjson/document.h @@ -47,6 +47,11 @@ RAPIDJSON_DIAG_OFF(effc++) #include // std::move #endif +#define RAPIDJSON_USE_MEMBERS_MAP +#ifdef RAPIDJSON_USE_MEMBERS_MAP +#include +#endif + RAPIDJSON_NAMESPACE_BEGIN // Forward declaration. @@ -404,6 +409,24 @@ inline GenericStringRef StringRef(const std::basic_string& s } #endif +#ifdef RAPIDJSON_USE_MEMBERS_MAP +template +struct GenericMemberMap { + typedef typename Encoding::Ch Ch; + typedef GenericStringRef KeyType; + struct KeyLess { + bool operator()(const KeyType &s1, const KeyType &s2) const { + int cmp = std::memcmp(s1.s, s2.s, sizeof(Ch) * (s1.length < s2.length ? s1.length : s2.length)); + return cmp < 0 || (cmp == 0 && s1.length < s2.length); + } + }; + typedef std::pair Pair; + typedef typename Allocator::template rebind::other AllocatorType; + typedef std::multimap Map; + typedef typename Map::iterator Iterator; +}; +#endif + /////////////////////////////////////////////////////////////////////////////// // GenericValue type traits namespace internal { @@ -651,22 +674,12 @@ class GenericValue { template GenericValue(const GenericValue& rhs, Allocator& allocator, bool copyConstStrings = false) { switch (rhs.GetType()) { - case kObjectType: { - SizeType count = rhs.data_.o.size; - Member* lm = reinterpret_cast(allocator.Malloc(count * sizeof(Member))); - const typename GenericValue::Member* rm = rhs.GetMembersPointer(); - for (SizeType i = 0; i < count; i++) { - new (&lm[i].name) GenericValue(rm[i].name, allocator, copyConstStrings); - new (&lm[i].value) GenericValue(rm[i].value, allocator, copyConstStrings); - } - data_.f.flags = kObjectFlag; - data_.o.size = data_.o.capacity = count; - SetMembersPointer(lm); - } + case kObjectType: + DoCopyMembers(rhs, allocator, copyConstStrings); break; case kArrayType: { SizeType count = rhs.data_.a.size; - GenericValue* le = reinterpret_cast(allocator.Malloc(count * sizeof(GenericValue))); + GenericValue* le = allocator.template Allocate(count); const GenericValue* re = rhs.GetElementsPointer(); for (SizeType i = 0; i < count; i++) new (&le[i]) GenericValue(re[i], allocator, copyConstStrings); @@ -810,9 +823,7 @@ class GenericValue { break; case kObjectFlag: - for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m) - m->~Member(); - Allocator::Free(GetMembersPointer()); + DoClearMembers(true); break; case kCopyStringFlag: @@ -1177,10 +1188,7 @@ class GenericValue { */ GenericValue& MemberReserve(SizeType newCapacity, Allocator &allocator) { RAPIDJSON_ASSERT(IsObject()); - if (newCapacity > data_.o.capacity) { - SetMembersPointer(reinterpret_cast(allocator.Realloc(GetMembersPointer(), data_.o.capacity * sizeof(Member), newCapacity * sizeof(Member)))); - data_.o.capacity = newCapacity; - } + DoReserveMembers(newCapacity, allocator); return *this; } @@ -1254,11 +1262,7 @@ class GenericValue { MemberIterator FindMember(const GenericValue& name) { RAPIDJSON_ASSERT(IsObject()); RAPIDJSON_ASSERT(name.IsString()); - MemberIterator member = MemberBegin(); - for ( ; member != MemberEnd(); ++member) - if (name.StringEqual(member->name)) - break; - return member; + return DoFindMember(name); } template ConstMemberIterator FindMember(const GenericValue& name) const { return const_cast(*this).FindMember(name); } @@ -1287,14 +1291,7 @@ class GenericValue { GenericValue& AddMember(GenericValue& name, GenericValue& value, Allocator& allocator) { RAPIDJSON_ASSERT(IsObject()); RAPIDJSON_ASSERT(name.IsString()); - - ObjectData& o = data_.o; - if (o.size >= o.capacity) - MemberReserve(o.capacity == 0 ? kDefaultObjectCapacity : (o.capacity + (o.capacity + 1) / 2), allocator); - Member* members = GetMembersPointer(); - members[o.size].name.RawAssign(name); - members[o.size].value.RawAssign(value); - o.size++; + DoAddMember(name, value, allocator); return *this; } @@ -1428,9 +1425,7 @@ class GenericValue { */ void RemoveAllMembers() { RAPIDJSON_ASSERT(IsObject()); - for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m) - m->~Member(); - data_.o.size = 0; + DoClearMembers(false); } //! Remove a member in object by its name. @@ -1474,14 +1469,7 @@ class GenericValue { RAPIDJSON_ASSERT(data_.o.size > 0); RAPIDJSON_ASSERT(GetMembersPointer() != 0); RAPIDJSON_ASSERT(m >= MemberBegin() && m < MemberEnd()); - - MemberIterator last(GetMembersPointer() + (data_.o.size - 1)); - if (data_.o.size > 1 && m != last) - *m = *last; // Move the last one to this place - else - m->~Member(); // Only one left, just destroy - --data_.o.size; - return m; + return DoRemoveMember(m); } //! Remove a member from an object by iterator. @@ -1513,13 +1501,7 @@ class GenericValue { RAPIDJSON_ASSERT(first >= MemberBegin()); RAPIDJSON_ASSERT(first <= last); RAPIDJSON_ASSERT(last <= MemberEnd()); - - MemberIterator pos = MemberBegin() + (first - MemberBegin()); - for (MemberIterator itr = pos; itr != last; ++itr) - itr->~Member(); - std::memmove(static_cast(&*pos), &*last, static_cast(MemberEnd() - last) * sizeof(Member)); - data_.o.size -= static_cast(last - first); - return pos; + return DoEraseMember(first, last); } //! Erase a member in object by its name. @@ -1614,7 +1596,7 @@ class GenericValue { GenericValue& Reserve(SizeType newCapacity, Allocator &allocator) { RAPIDJSON_ASSERT(IsArray()); if (newCapacity > data_.a.capacity) { - SetElementsPointer(reinterpret_cast(allocator.Realloc(GetElementsPointer(), data_.a.capacity * sizeof(GenericValue), newCapacity * sizeof(GenericValue)))); + SetElementsPointer(allocator.Reallocate(GetElementsPointer(), data_.a.capacity, newCapacity)); data_.a.capacity = newCapacity; } return *this; @@ -2030,11 +2012,255 @@ class GenericValue { RAPIDJSON_FORCEINLINE Member* GetMembersPointer() const { return RAPIDJSON_GETPOINTER(Member, data_.o.members); } RAPIDJSON_FORCEINLINE Member* SetMembersPointer(Member* members) { return RAPIDJSON_SETPOINTER(Member, data_.o.members, members); } +#ifdef RAPIDJSON_USE_MEMBERS_MAP + typedef typename GenericMemberMap::Map MemberMap; + typedef typename GenericMemberMap::KeyLess MemberMapKeyLess; + typedef typename GenericMemberMap::Iterator MemberMapIterator; + typedef typename GenericMemberMap::Pair MemberMapPair; + + RAPIDJSON_FORCEINLINE size_t GetMapAllocSize(SizeType capacity) { + return RAPIDJSON_ALIGN(sizeof(MemberMap)) + + RAPIDJSON_ALIGN(sizeof(SizeType)) + + RAPIDJSON_ALIGN(capacity * sizeof(Member)) + + capacity * sizeof(MemberMapIterator); + } + + RAPIDJSON_FORCEINLINE SizeType &GetMapCapacity(MemberMap* map) { + return *reinterpret_cast(reinterpret_cast(map) + + RAPIDJSON_ALIGN(sizeof(MemberMap))); + } + + RAPIDJSON_FORCEINLINE Member* GetMapMembers(MemberMap* map) { + return reinterpret_cast(reinterpret_cast(map) + + RAPIDJSON_ALIGN(sizeof(MemberMap)) + + RAPIDJSON_ALIGN(sizeof(SizeType))); + } + RAPIDJSON_FORCEINLINE MemberMap* GetMembersMap(Member* members) { + return reinterpret_cast(reinterpret_cast(members) - + RAPIDJSON_ALIGN(sizeof(SizeType)) - + RAPIDJSON_ALIGN(sizeof(MemberMap))); + } + + RAPIDJSON_FORCEINLINE MemberMapIterator* GetMapIterators(MemberMap* map, SizeType capacity) { + return reinterpret_cast(reinterpret_cast(map) + + RAPIDJSON_ALIGN(sizeof(MemberMap)) + + RAPIDJSON_ALIGN(sizeof(SizeType)) + + RAPIDJSON_ALIGN(capacity * sizeof(Member))); + } + RAPIDJSON_FORCEINLINE MemberMapIterator* GetMapIterators(MemberMap* map) { + return GetMapIterators(map, GetMapCapacity(map)); + } + + MemberMap* DoReallocMap(MemberMap* oldMap, SizeType newCapacity, Allocator& allocator) { + MemberMap* newMap; + if (oldMap) { + // An (std::)map can't be reallocated (supposedly), + // let's save/restore it before/after with a double swap + MemberMap tmpMap(MemberMapKeyLess(), allocator); + tmpMap.swap(*oldMap); + oldMap->~MemberMap(); + SizeType oldCapacity = GetMapCapacity(oldMap); + void *newRoom = allocator.Realloc(oldMap, + GetMapAllocSize(oldCapacity), + GetMapAllocSize(newCapacity)); + newMap = new(newRoom) MemberMap(MemberMapKeyLess(), allocator); + // Move the old iterators to their new place + std::memmove(GetMapIterators(newMap, newCapacity), + GetMapIterators(newMap, oldCapacity), + oldCapacity * sizeof(MemberMapIterator)); + // Restore the old (std::)map + newMap->swap(tmpMap); + } + else { + void *newRoom = allocator.Malloc(GetMapAllocSize(newCapacity)); + newMap = new(newRoom) MemberMap(MemberMapKeyLess(), allocator); + } + GetMapCapacity(newMap) = newCapacity; + return newMap; + } + + Member* DoAllocMembers(SizeType capacity, Allocator& allocator) { + return GetMapMembers(DoReallocMap(NULL, capacity, allocator)); + } + + void DoReserveMembers(SizeType newCapacity, Allocator& allocator) { + ObjectData& o = data_.o; + if (newCapacity > o.capacity) { + Member* oldMembers = GetMembersPointer(); + MemberMap* oldMap = oldMembers ? GetMembersMap(oldMembers) : 0; + MemberMap* newMap = DoReallocMap(oldMap, newCapacity, allocator); + RAPIDJSON_SETPOINTER(Member, o.members, GetMapMembers(newMap)); + o.capacity = newCapacity; + } + } + + template + MemberIterator DoFindMember(const GenericValue& name) { + if (Member* members = GetMembersPointer()) { + MemberMap* map = GetMembersMap(members); + StringRefType k(name.GetString(), name.GetStringLength()); + MemberMapIterator mit = map->find(k); + if (mit != map->end()) { + return MemberIterator(members + mit->second); + } + } + return MemberEnd(); + } +#else // !RAPIDJSON_USE_MEMBERS_MAP + Member* DoAllocMembers(SizeType capacity, Allocator& allocator) { + return allocator.template Allocate(capacity); + } + + void DoReserveMembers(SizeType newCapacity, Allocator& allocator) { + ObjectData& o = data_.o; + if (newCapacity > o.capacity) { + Member* newMembers = allocator.Reallocate(GetMembersPointer(), o.capacity, newCapacity); + RAPIDJSON_SETPOINTER(Member, o.members, newMembers); + o.capacity = newCapacity; + } + } + + template + MemberIterator DoFindMember(const GenericValue& name) { + MemberIterator member = MemberBegin(); + for ( ; member != MemberEnd(); ++member) + if (name.StringEqual(member->name)) + break; + return member; + } +#endif + + void DoAddMember(GenericValue& name, GenericValue& value, Allocator& allocator) { + ObjectData& o = data_.o; + if (o.size >= o.capacity) + DoReserveMembers(o.capacity ? (o.capacity + (o.capacity + 1) / 2) : kDefaultObjectCapacity, allocator); + Member* members = GetMembersPointer(); + Member* m = members + o.size; + m->name.RawAssign(name); + m->value.RawAssign(value); +#ifdef RAPIDJSON_USE_MEMBERS_MAP + MemberMap* map = GetMembersMap(members); + MemberMapIterator* mit = GetMapIterators(map); + StringRefType k(m->name.GetString(), m->name.GetStringLength()); + mit[o.size] = map->insert(MemberMapPair(k, o.size)); +#endif + ++o.size; + } + + MemberIterator DoRemoveMember(MemberIterator m) { + ObjectData& o = data_.o; + Member* members = GetMembersPointer(); + MemberIterator last(members + (o.size - 1)); + if (o.size > 1 && m != last) { +#ifdef RAPIDJSON_USE_MEMBERS_MAP + MemberMap* map = GetMembersMap(members); + MemberMapIterator* mit = GetMapIterators(map); + SizeType mpos = static_cast(&*m - members); + map->erase(mit[mpos]); + mit[mpos] = mit[&*last - members]; + mit[mpos]->second = mpos; +#endif + *m = *last; // Move the last one to this place + } + else { +#ifdef RAPIDJSON_USE_MEMBERS_MAP + MemberMap* map = GetMembersMap(members); + MemberMapIterator* mit = GetMapIterators(map); + map->erase(mit[m - MemberBegin()]); +#endif + m->~Member(); // Only one left, just destroy + } + --o.size; + return m; + } + + MemberIterator DoEraseMember(ConstMemberIterator first, ConstMemberIterator last) { + ObjectData& o = data_.o; + MemberIterator beg = MemberBegin(), + pos = beg + (first - beg), + end = MemberEnd(); +#ifdef RAPIDJSON_USE_MEMBERS_MAP + MemberMap* map = GetMembersMap(GetMembersPointer()); + MemberMapIterator *mit = GetMapIterators(map); +#endif + for (MemberIterator itr = pos; itr != last; ++itr) { +#ifdef RAPIDJSON_USE_MEMBERS_MAP + map->erase(mit[itr - beg]); +#endif + itr->~Member(); + } +#ifdef RAPIDJSON_USE_MEMBERS_MAP + if (pos != last) { + MemberIterator next = pos + (last - first); + for (MemberIterator itr = pos; next != end; ++itr, ++next) { + std::memcpy(static_cast(&*itr), &*next, sizeof(Member)); + SizeType mpos = static_cast(itr - beg); + mit[mpos] = mit[next - beg]; + mit[mpos]->second = mpos; + } + } +#else + std::memmove(static_cast(&*pos), &*last, + static_cast(end - last) * sizeof(Member)); +#endif + o.size -= static_cast(last - first); + return pos; + } + + template + void DoCopyMembers(const GenericValue& rhs, Allocator& allocator, bool copyConstStrings) { + RAPIDJSON_ASSERT(rhs.GetType() == kObjectType); + + data_.f.flags = kObjectFlag; + SizeType count = rhs.data_.o.size; + Member* m = DoAllocMembers(count, allocator); + const typename GenericValue::Member* rm = rhs.GetMembersPointer(); +#ifdef RAPIDJSON_USE_MEMBERS_MAP + MemberMap* map = GetMembersMap(m); + MemberMapIterator* mit = GetMapIterators(map); +#endif + for (SizeType i = 0; i < count; i++) { + new (&m[i].name) GenericValue(rm[i].name, allocator, copyConstStrings); + new (&m[i].value) GenericValue(rm[i].value, allocator, copyConstStrings); +#ifdef RAPIDJSON_USE_MEMBERS_MAP + StringRefType k(m[i].name.GetString(), m[i].name.GetStringLength()); + mit[i] = map->insert(MemberMapPair(k, i)); +#endif + } + data_.o.size = data_.o.capacity = count; + SetMembersPointer(m); + } + + void DoClearMembers(bool free) { + if (Member* members = GetMembersPointer()) { + ObjectData& o = data_.o; + for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m) + m->~Member(); + if (free) { + RAPIDJSON_SETPOINTER(Member, o.members, 0); +#ifdef RAPIDJSON_USE_MEMBERS_MAP + MemberMap* map = GetMembersMap(members); + map->~MemberMap(); + Allocator::Free(map); +#else + Allocator::Free(members); +#endif + o.capacity = 0; + } +#ifdef RAPIDJSON_USE_MEMBERS_MAP + else { + GetMembersMap(members)->clear(); + } +#endif + o.size = 0; + } + } + // Initialize this value as array with initial data, without calling destructor. void SetArrayRaw(GenericValue* values, SizeType count, Allocator& allocator) { data_.f.flags = kArrayFlag; if (count) { - GenericValue* e = static_cast(allocator.Malloc(count * sizeof(GenericValue))); + GenericValue* e = allocator.template Allocate(count); SetElementsPointer(e); std::memcpy(static_cast(e), values, count * sizeof(GenericValue)); } @@ -2047,13 +2273,23 @@ class GenericValue { void SetObjectRaw(Member* members, SizeType count, Allocator& allocator) { data_.f.flags = kObjectFlag; if (count) { - Member* m = static_cast(allocator.Malloc(count * sizeof(Member))); - SetMembersPointer(m); + Member* m = DoAllocMembers(count, allocator); std::memcpy(static_cast(m), members, count * sizeof(Member)); +#ifdef RAPIDJSON_USE_MEMBERS_MAP + MemberMap* map = GetMembersMap(m); + MemberMapIterator* mit = GetMapIterators(map); + for (SizeType i = 0; i < count; i++) { + StringRefType k(m[i].name.GetString(), m[i].name.GetStringLength()); + mit[i] = map->insert(MemberMapPair(k, i)); + } +#endif + data_.o.size = data_.o.capacity = count; + SetMembersPointer(m); } - else + else { + data_.o.size = data_.o.capacity = 0; SetMembersPointer(0); - data_.o.size = data_.o.capacity = count; + } } //! Initialize this value as constant string, without calling destructor. @@ -2073,7 +2309,7 @@ class GenericValue { } else { data_.f.flags = kCopyStringFlag; data_.s.length = s.length; - str = static_cast(allocator.Malloc((s.length + 1) * sizeof(Ch))); + str = allocator.template Allocate(s.length + 1); SetStringPointer(str); } std::memcpy(str, s, s.length * sizeof(Ch)); diff --git a/include/rapidjson/rapidjson.h b/include/rapidjson/rapidjson.h index 549936ffe..240c2db15 100644 --- a/include/rapidjson/rapidjson.h +++ b/include/rapidjson/rapidjson.h @@ -535,6 +535,10 @@ RAPIDJSON_NAMESPACE_END /////////////////////////////////////////////////////////////////////////////// // C++11 features +#ifndef RAPIDJSON_HAS_CXX11 +#define RAPIDJSON_HAS_CXX11 (__cplusplus >= 201103L) +#endif + #ifndef RAPIDJSON_HAS_CXX11_RVALUE_REFS #if defined(__clang__) #if __has_feature(cxx_rvalue_references) && \ @@ -567,7 +571,7 @@ RAPIDJSON_NAMESPACE_END #if RAPIDJSON_HAS_CXX11_NOEXCEPT #define RAPIDJSON_NOEXCEPT noexcept #else -#define RAPIDJSON_NOEXCEPT /* noexcept */ +#define RAPIDJSON_NOEXCEPT throw() #endif // RAPIDJSON_HAS_CXX11_NOEXCEPT // no automatic detection, yet @@ -612,7 +616,8 @@ RAPIDJSON_NAMESPACE_END #if RAPIDJSON_HAS_CXX11_NOEXCEPT #define RAPIDJSON_NOEXCEPT_ASSERT(x) #else -#define RAPIDJSON_NOEXCEPT_ASSERT(x) RAPIDJSON_ASSERT(x) +#include +#define RAPIDJSON_NOEXCEPT_ASSERT(x) assert(x) #endif // RAPIDJSON_HAS_CXX11_NOEXCEPT #else #define RAPIDJSON_NOEXCEPT_ASSERT(x) RAPIDJSON_ASSERT(x) diff --git a/test/perftest/perftest.h b/test/perftest/perftest.h index 953f95de8..3c0bd0868 100644 --- a/test/perftest/perftest.h +++ b/test/perftest/perftest.h @@ -130,7 +130,8 @@ class PerfTest : public ::testing::Test { "integers.json", "mixed.json", "nulls.json", - "paragraphs.json" + "paragraphs.json", + "alotofkeys.json" }; for (size_t j = 0; j < sizeof(typesfilenames) / sizeof(typesfilenames[0]); j++) { @@ -158,7 +159,7 @@ class PerfTest : public ::testing::Test { free(whitespace_); json_ = 0; whitespace_ = 0; - for (size_t i = 0; i < 7; i++) { + for (size_t i = 0; i < 8; i++) { free(types_[i]); types_[i] = 0; } @@ -174,8 +175,8 @@ class PerfTest : public ::testing::Test { size_t length_; char *whitespace_; size_t whitespace_length_; - char *types_[7]; - size_t typesLength_[7]; + char *types_[8]; + size_t typesLength_[8]; static const size_t kTrialCount = 1000; }; diff --git a/test/perftest/rapidjsontest.cpp b/test/perftest/rapidjsontest.cpp index 9492cc57d..ee0008b65 100644 --- a/test/perftest/rapidjsontest.cpp +++ b/test/perftest/rapidjsontest.cpp @@ -26,6 +26,7 @@ #include "rapidjson/memorystream.h" #include +#include #ifdef RAPIDJSON_SSE2 #define SIMD_SUFFIX(name) name##_SSE2 @@ -52,7 +53,7 @@ class RapidJson : public PerfTest { // Parse as a document EXPECT_FALSE(doc_.Parse(json_).HasParseError()); - for (size_t i = 0; i < 7; i++) + for (size_t i = 0; i < 8; i++) EXPECT_FALSE(typesDoc_[i].Parse(types_[i]).HasParseError()); } @@ -68,7 +69,7 @@ class RapidJson : public PerfTest { protected: char *temp_; Document doc_; - Document typesDoc_[7]; + Document typesDoc_[8]; }; TEST_F(RapidJson, SIMD_SUFFIX(ReaderParseInsitu_DummyHandler)) { @@ -335,6 +336,23 @@ TEST_F(RapidJson, DocumentAccept) { } } +TEST_F(RapidJson, DocumentFind) { + typedef typename Document::ValueType ValueType; + typedef typename ValueType::ConstMemberIterator ConstMemberIterator; + const Document &doc = typesDoc_[7]; // alotofkeys.json + if (doc.IsObject()) { + std::vector keys; + for (ConstMemberIterator it = doc.MemberBegin(); it != doc.MemberEnd(); ++it) { + keys.push_back(&it->name); + } + for (size_t i = 0; i < kTrialCount; i++) { + for (size_t j = 0; j < keys.size(); j++) { + EXPECT_TRUE(doc.FindMember(*keys[j]) != doc.MemberEnd()); + } + } + } +} + struct NullStream { typedef char Ch; diff --git a/test/unittest/unittest.h b/test/unittest/unittest.h index 84c1b7348..0afac09cb 100644 --- a/test/unittest/unittest.h +++ b/test/unittest/unittest.h @@ -122,6 +122,9 @@ class AssertException : public std::logic_error { #ifndef RAPIDJSON_ASSERT #define RAPIDJSON_ASSERT(x) (!(x) ? throw AssertException(RAPIDJSON_STRINGIFY(x)) : (void)0u) +#ifndef RAPIDJSON_ASSERT_THROWS +#define RAPIDJSON_ASSERT_THROWS +#endif #endif class Random {