summaryrefslogtreecommitdiff
path: root/tools/perf/scripts/python/stackcollapse.py
blob: b1c4def1410a8aea617b0843b681eb7435a892dc (plain)
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
# stackcollapse.py - format perf samples with one line per distinct call stack
# SPDX-License-Identifier: GPL-2.0
#
# This script's output has two space-separated fields.  The first is a semicolon
# separated stack including the program name (from the "comm" field) and the
# function names from the call stack.  The second is a count:
#
#  swapper;start_kernel;rest_init;cpu_idle;default_idle;native_safe_halt 2
#
# The file is sorted according to the first field.
#
# Input may be created and processed using:
#
#  perf record -a -g -F 99 sleep 60
#  perf script report stackcollapse > out.stacks-folded
#
# (perf script record stackcollapse works too).
#
# Written by Paolo Bonzini <pbonzini@redhat.com>
# Based on Brendan Gregg's stackcollapse-perf.pl script.

from __future__ import print_function

import os
import sys
from collections import defaultdict
from optparse import OptionParser, make_option

sys.path.append(os.environ['PERF_EXEC_PATH'] + \
    '/scripts/python/Perf-Trace-Util/lib/Perf/Trace')

from perf_trace_context import *
from Core import *
from EventClass import *

# command line parsing

option_list = [
    # formatting options for the bottom entry of the stack
    make_option("--include-tid", dest="include_tid",
                 action="store_true", default=False,
                 help="include thread id in stack"),
    make_option("--include-pid", dest="include_pid",
                 action="store_true", default=False,
                 help="include process id in stack"),
    make_option("--no-comm", dest="include_comm",
                 action="store_false", default=True,
                 help="do not separate stacks according to comm"),
    make_option("--tidy-java", dest="tidy_java",
                 action="store_true", default=False,
                 help="beautify Java signatures"),
    make_option("--kernel", dest="annotate_kernel",
                 action="store_true", default=False,
                 help="annotate kernel functions with _[k]")
]

parser = OptionParser(option_list=option_list)
(opts, args) = parser.parse_args()

if len(args) != 0:
    parser.error("unexpected command line argument")
if opts.include_tid and not opts.include_comm:
    parser.error("requesting tid but not comm is invalid")
if opts.include_pid and not opts.include_comm:
    parser.error("requesting pid but not comm is invalid")

# event handlers

lines = defaultdict(lambda: 0)

def process_event(param_dict):
    def tidy_function_name(sym, dso):
        if sym is None:
            sym = '[unknown]'

        sym = sym.replace(';', ':')
        if opts.tidy_java:
            # the original stackcollapse-perf.pl script gives the
            # example of converting this:
            #    Lorg/mozilla/javascript/MemberBox;.<init>(Ljava/lang/reflect/Method;)V
            # to this:
            #    org/mozilla/javascript/MemberBox:.init
            sym = sym.replace('<', '')
            sym = sym.replace('>', '')
            if sym[0] == 'L' and sym.find('/'):
                sym = sym[1:]
            try:
                sym = sym[:sym.index('(')]
            except ValueError:
                pass

        if opts.annotate_kernel and dso == '[kernel.kallsyms]':
            return sym + '_[k]'
        else:
            return sym

    stack = list()
    if 'callchain' in param_dict:
        for entry in param_dict['callchain']:
            entry.setdefault('sym', dict())
            entry['sym'].setdefault('name', None)
            entry.setdefault('dso', None)
            stack.append(tidy_function_name(entry['sym']['name'],
                                            entry['dso']))
    else:
        param_dict.setdefault('symbol', None)
        param_dict.setdefault('dso', None)
        stack.append(tidy_function_name(param_dict['symbol'],
                                        param_dict['dso']))

    if opts.include_comm:
        comm = param_dict["comm"].replace(' ', '_')
        sep = "-"
        if opts.include_pid:
            comm = comm + sep + str(param_dict['sample']['pid'])
            sep = "/"
        if opts.include_tid:
            comm = comm + sep + str(param_dict['sample']['tid'])
        stack.append(comm)

    stack_string = ';'.join(reversed(stack))
    lines[stack_string] = lines[stack_string] + 1

def trace_end():
    list = sorted(lines)
    for stack in list:
        print("%s %d" % (stack, lines[stack]))
uL6Dl8 W5 .& 1Vr%31ŐrHD2d /K ^g>c ER)Vok4[;w7e++ksoIGjAbE"^ǒY/ɲ9oۼw_G<ڻ)qB͡)Q_vJEfMb`2tS0V:tX\>R$4 K$R@HI= \H "Ax\uO['ZmZw <뵎 0 ,441vЛ5͊}Ы|_0X{ۉl Q'pDIHT9 ZѩTh liq]-m8 ֖X_#|GdW%iLo{Lmr i6]w~u 4 @zxH٩d'ٵVE$_pVwHB΢^YqȊ7O|J(3%(y>uŻ0#6Zҟ20|k=iGm=TG͇hũe= s#<lnPm3_C`?& &%NWJ*LRfL}t q%˕q9D$־@rK5ONA3-tO{ bB:Eў׭ v81Prj/Vj1ic^:Uk6"usϤv^fe,ɖJ2NΐXC6yyпv,Ww%StX7?lGz;~/Ak'k/j o;w@&ԗ$=5qLw_&,spFR"1S$gD41#6Dt1($2ĀSj&KX1ȼτ@*-UrI`ȁ1&ncB]4 T/:SE ۧqFGc/涛,[Z邠f:n-{wj'='ËO{Ãfu3g !-EbĊOë7#i=SU(L}7 !w/mEO¾Dؐ-sE]k.ЦӳٸŊW܆mM-26Ju*l0U̽L_8 kZoS&i5 l:x`I6AD?'fr6TY}Ab c 'S!&yobKH1 /Eg}NdGq*uY3^Wz/K}ڹО gTh?DlliJ5xBm<A{bZ \R@D4>Gя2aE@caKB1oJАߚ=yE iB9i Y'3j܌X)nP^ma)`5ČjGOhIƾ_DOq>XT1x^a*}~ ;jzĨp(؅QX>!3CiḊ=e췃ǥZnņ'b|ǒxwtph;7_WoĊͲ5NS\gf|8}i>) !-#Ș' `#Dhţ"r3:8xx> GTXs%NOڢsr+FqY Wf0<&NFH [<<촶.NxX3~FYdn;Q|i:C:9aMv/κ3qihq `K ԶH K 2~ꏆsBF,]us[E+6dJUT.Q࠳_u~07kgecͶ 3@@Ylp-Xzl֮iJk6)&!@RkD g8XiE${wu9_MF*nvA/N@;$-huENB@ï1a<Ɵ? \"']Ll4(g?KǘJ"I3]>S$Z<0bG灖hŠVx{lMKbSВt Xq5ڑd#& 60lMӓnG:cqW{Sb5Zm>k@)*lP8OE)[%^u|S@(#q>ɘYG!4Ě/J"B&Kļ4+3&| 1QG>J7S"ڶda^J$-qӀ /+0QH2"PqClfK#C~8CLn9W\ >uIgZˍ`OO +lp>m#J1,WXF[ECX2/ oiɘX<ƔS ]N0gz Af ݎXRMyi@DW!xa6st\6쐊'8{MQchw;O|?[rJEJ~nH2 0S1%q 0{rDCwHI?7XR8" xod: 6ttiD6[⼧.M5 |N˞'Һ@ۊT:t.cf#RRWτZ/{5 )AFr#͢]xtp19 a}s#b<5(tZh pճ64yU$T\.gHvmd h{P7s VRڮf&E=Z[HT's2Н@ 2"Rn@,k˒JTVzNjm88xrBc2yГh̢vVƛUOzvi_8ڱ%Ga tYk< YVUjjJ^K$dQ_n?[tCqh3¸mDz}+v-{2חZ?Jc63jv6a`;o;(}GN>=IIܹrySjǝrCBbasZn/m o,o [ًޛ<  VY!Zmh;2 !8Cq*W{H-q[j>GRZ>Ȧ#{2^D]goߏ:tX۬Exn5'L0O$ݽi݆ڿ#$+M!v7ˁOfF?cKW:sZXmi-Rh)<̈́ZaLCHQ㡪U!BHuʪߧV!B; /Cu|P,WUd̛j[ƚЛQ^}ݝ?#qLJD}IVP2H>[ȺQWĊ sБK=!q,1YJsެZj7U())CU۪_!aS7ՕI? {hPyʚvtgzQfwpgs$0a8 =ȕI67iHB]`٩VUua.~E,Pk{w s C@W/瑡9U7ʤ͋?mAY 2+>lҡD* 㥈(j2^! ٧ndk-rqj.Lf2@JuCA5+EHdlkN͢@-~`)* gG0Nd@/I+Y'WM'YH2gj"r0&ݑx#Ot:PvtE|es 6=!X>L3٤j&v1kT-pܥRg' T%#3ua+r-IIEHsH(Х%[X9Q6"cb>,t^Qd5 pU ig[B[8$AB' >Cd 7Ii_QM|=3SA3')Ŏ.}^h _f ¨=29\o=ꨡZeHz~V~]R!UWPh4RZ&vy9X%d2883,2= ՐXLspϽ g֗,=4&pE.y##V'TT{gm%v'#iCxu}v~/z x'km5)4}U!IjTOQEtM#_{C7z13fo0"-]Y{۱Ic̜Q{ߋ~OZd˚ZFфd*784˨ۂEkNdM}a(d}X؋TdŁg NE^tWUU]Sl9<2FwxexB9Ri ȨK&ya]'(+ ^Uo:W VfW702O!*UjWc_P{^ {ӈl9K赅'JAȴӺ#\K3qT-ܭ)D#qeh.D/ v晔w׎ӌ]06ŵOXC|LFZjUFNU@>)eefchvy_T^%j b:9-24_g z'do-6+v.5Wh(^!enet~yٸбiouA:C G M!࿰nCŒ>p0E!$|j A kO:KRl e+? L8ILȳl؏ptH܅`w(e4r{ W-Bo3 *':4$H& 3:D33@VѯMEC~m"i@oUD7in5ZmK>BmvNގ6Hx MFrp3 YxI'ӊ%[ZzBwV^ }b kHpZեҭO2|`\,{[ 䅽 E}yv+RQ٬+$*}jjgWabcLi h W(\PAĥHz|^SbD{g]7~k;`W+:.*؀pqvd:$JZRkJblpIAtMS$()sRM +8&yl:sCzOBw\+j%@w:j .vРK`BO 5oEj ˆuqBFEszWr\IڭjwC0$fwh|:hSu]ΧKQm6{g%s;%R\nN/Ȧ-tMxdތίF7*PMIGdK" ydxI%I}\l~4-jQi~A_Eda6K3!G[Jfr,˥\)tC[4? 8hYzIEժLllHlޝwA%Nj0RD*dS2 GMfl#Z&1L&?aB[gFqıH*'yu~}?}ue[^͓`(3 bGSw-Rute J(P~l~Л=4=rS;2s"&@| v;s9UH^PL%L!Ju@VڨdkR fdHV΁e:hY2G.Y\1+{Q 8!ѴEfxؐ4sw'yыvKMϱtF,#VW9# xlIm,k?gюe#3j .k.bʰ=H{wt߫Ui8NKtq @i1-^מV*[}rih\et&L ꑍb`l6玙})K(@;U t[~@[iľ|o5'kw]|H]|#͢ΗV]Eqf"VO_]N^=fQM&ډ2emTnm/) d<w\ť9'Jꍳ^hkCx'.CO°AAuM洃9H4o\!RТWy.`֥LJX$5tljx_@ 1˭6س>l!dybb?\{6rG]Vƕ :9qBnij7q ˇ;J3>wT޸ϝjK[ÖsrS5z $uI@B0 ˑV Ϣ/b H<[94VoSH ;b"( |^Loo'/3VE+#*@QIĦ+t 藅~#}$j"&cj֜wtwFtwZci+M3>@\9eYg\g`|kMu Fِ 5xd$:9_ l"}&f+;|b;"Vq٨0?L~_HfTJ-*/Ǡ@nUL39|v A>5Y)̱,}QȨF!Ăw}HR#{ qN,X! ⽹k u= աZYFv^ sݳzؤ]yOɏ,HcOG?jll!f!VN;U#<%H>p7M xc;27o)XBhVԪ`IRPoHA1':^}1)HZI]sKbߺۙCi h8hjS7cUvj,U dYsT!AiUոpBlG32"|DJ{X%1A ^43^ħҦYK)[| ~?w[ F [7}BfO`)C-QcNPAT},t(wOng ?Ivb~ǁG,/MߋiE&O{@rW67nofIU*]VmZ遅7?-kawRs w#%}`K ɤcZ<0~wI[Z;T\YJT}r͉,.Y^dǁ6$ˡI(䇋ӳ0!$fEJ1i7d^ чjxvzfVoYtG3Hd~fJpۡqI.{cCeJ3hx!eE./vĉO`nCJaUׇKwYyx+GrX].s3y,&.E)_E҃^ Ѱx:ͨ}x_"e

ͳM%U&k^]-Tg`O#wrbrFkѩ 3NIM`I `*P?$df[HzjCNj3_!]dcg! |,Nݍ(H #_E'BmZ uf:B8BLkQS(7(?/_9vb.:b$ yBࣩ%$o3:]wsajۉ7N񁘿TlW)n ok{/YDz,@2J8Q`? }IjrLB~.fsK3(G|vJ%6+^NV: ph1҈58Z_hE!]V8\Ndkg [mM`&@|䦮0}v?=o~LӒkuxm͸W WE8PKjrj0dG ti%r8=:\"- N4D&# &V.iDJyLHUDTBU+9bAh]%Yn9F>KJͱ7T1i"`dl6uI+7n*!0JZgwn={v 9"c6 TgpeA,t.Q8ICݖ<{רg_gE0 naZܼW?H^F+dw09eY1%#_đ]}AOR`XM7?XUqtٻ#"{;TVi{ۣ-bz{o'u5⩵v$(NiYeT^n"H0&GxcRd$W[;:n7.o5D6uZwe{Whk~Sՠsc2Q-ӆn&Ah|PUր$ٚGp aӼ}&z!C^nhUٙN;XQ_gЦ`]zKfIOɚ_N/'S.0MҳW l 'O?c`x<<=gȒ2|ZwiCr:ZR&0;&@=r8l=Y@VU# QI7RqyUWA381&K7;<+p~ ) o1Xx~%r`ҊVdgkGZuoGlbU.Ta|Kv` 6Hv1K(!sSܢ34iQjCzrQ]JYN0֙%sjl^\Z-}UorD|a(\:ppFsِW@5ZUWNBgUwCF[b# Rr8Xi>撳IO@*X Cci`? [7T ̵ɾ:G2dUڟ +$KAl# hn5+BzPa2j`eShz= 7PO&]V0b@?n)=R|# #AX) {5v D@𰳷d!Q%bG*=iG :akYFO^7ˮuHԪ~O3RciܭqLSfjO$Sq]tܕ=3 TŤAZlM̴GsDzh|B)3OaYLZB~c[U!]x1m'0"i8;isS$+{6ܷl*."$?w6skwiG^ҍ-#U֪EgMv@Xy )Iv,z$]ş4o%/$͕ ,+DAs8ؙR;?Sz}4U=&ruSzAWvnś60A+yW,ssS$Gv:[~XH}HSwOt${%݈<[#? DFT*S,O?eM=S'aղH:^qfBiPrxlؾ]Y0w%]ew oPQl#)!ЦVZ 5?!~>^L }' $+E=[Ҭ,MaRJʳ[u0(1 {8\)7"c AuJ]iyg2݌UB4%݃aLL\U@(U?PmMaP4Q[?TQ $_%ٸ+quA9[yջ%T8=OQ4)J WaarE:ۋL0Ϳ"; epO>>o R.4~Ԫ1zYZ Y"JkX#-!t%GvM He.UםItoK턄*]-<3^kG< p?^ 67&VX*VH~ jSF%l\ڃ -(đ_?.e)/orKJFmd"JQ?[,WGih 4 _xB>l(%sap]H3nX4{G׷,[IxnSugnݝ %XabHjޭ%L}0?sk+:BSzRvFlY3 Mޮ1}oIVęhêJvHKE3/"$$f3FnOe}D%-y,<=7Vʵy&;F*)l" ^)+Zn z{F: ΉfRX!H5)YJ%pK[63̓&sh뫣 xw~b%~?=G tZQ-Z'PQHQG"wijEn2C~rXz:*]nQ2_%B0't.2+RW(. c(VmhnRRfl޳c[b܈GSn Y'nk9@'Z`7Bh50t)߆zsgam/oT~T_L $vqq } ʩ01:0]2򬾵XqO bsږ\E/v1OM#NIw9\v8|@ksB.$L̞[%LkD;U}_O ijׇP0#<3g~Է3 Y:jW;5Ǫc|SSujUW?/y3_5[4`N$ov!ּwb>% Gحս'?HX-)&oO"xw@#OٟH]0i(} 2i\mQw"BQt&ڼ܌5"wX`ޫ[ZNٺ^ƍ{̳^U~g-e\NgpG taB/ZilU <]YVwkW* y1!{BRxkm4cTsf)IuVY]8"m鋊}w[c2HD;[]ǹ w>T煻 ;ʢE9+1R+ske02#xe7΁܌@l :XvUfc?FI_]HNkKd(@;Zwbi3$CCF!ɾA t.ik)oҬ/T/aB|dEAO&vaIQĖ` #ql;qMGfhۚ #e_Vz4>=+['<)K~0I9(x޿u k 9NN؜ZPwDU ._nc)&GmnbN%D x6xv׉$xu",{V_v`&6<B;mHWEe@RZI^\glu֮ךlՅ Fp!zョWYテ eU6 jV)j{uhPݨgxa8DžAOÂJNzNM)_]Mv~> [!)BI>#_ω9ut  iLawDXet2<*e,!! _@޺/cB^9'? &yu @'ٖj lx9Q4XEdlF}>ĕݝM hQ&i x֟fJNd2(u ^l/*)Y@3PdHu)Ns#d\zD|`1' T^)sHQfw9, r=pMQuy->,+>}P058CƧ Sgf ̉mMALc' rKuaEˎ(6=TN4%FI<+rkD05aOVe ~԰/d]b4qCot}s(he2n[D+o7Sxf43 P/z8#=m.xQly?u[G0K'W#Rb: ] /=PQٺ s3juL9/={v"}uvmG)iܥE/\j v-]sބ:vWP޶# 76[ZYF t@3lx^u^$õF4[HϹϙF@ݲ|h@U`Q+6?\tn֤8̱K26 d8(l$hEuIg2ɀ|]R89cYQ-2 j Y|3N!㢂djJ̎Rh(^(4kV*^t1616M@ rg͕B}Q3̋Gxy)snÇLGh+%{1EX]& QBN6>ohl; BQ9aU6gczkծ7bWFM7zqmy7 kVDO3%(-RRENE?[ k3*?{|S;B[5d&ᩫF,2b/7)[Ϡ%JmtG<00ϝa؛&hmdYs粒LΟ., 9If& >)(C!Ln$.94Q4ǬQj)%p~)1*&#Ca٩T*g:I=__mؽwҩa?7 m."Xu{ as ƽ3ix$N]M$WUnygH^$8Y#+'׸$?1hvI^9@&oĕN)XuYEv`~3|Ƭe Zߟ6XhLXEԬ@OP;3?X c2Ia/w&Vڴz*#r)-5QwXVY/|z(7{Ξ$I-0NL&1P6m#쫹$8"Qe@*Uҷ X=?u.׊j#n}Er-^iּ#4wUjazCktB)2YLN(Irn U泌H39iqC6,Y)Es0^ڄ#&OF@d,<ߛ`fEb: .ʴ4y6r-znpOsNMLx{ ]tz7m*g"]LeV 'By߰ve!}ؚ7/yD^Qr5obV^~ItOYő0"opw6,6C/5nԵM82>gC¦J}UiV Z-9Q]t5cs*4zAbZ$hPfI|Qg#Q +ZIdN|\^Acz 2b~3O,XUըԋv%O>%|]1p$pƻ%%yqH  /omK΂ 32GՋ*-e(sZg~{ Z2~z2*l'Yfag%zP eW*c|p$1qj1UkaWUޘ&+Po3iZ.G*]4s \Aw&RJǭ]Y נBoF7{ e3P5׶sф*9\02i>kd06 {o\0K説7,-4v46UjVtFr!g}A޽BL RBRn٠ToɃ:J a\NLrGZ5ɉ@[4Np%Gy;IG̜t;G}k|}t %<ŵ5 [;bkT qԓB6fBI[]`r؛(]NgixAmp֮| D}tol[=d^]=[_ we8Qo!+褗:Zn 4?GM#iHn:1}3K麡g x 4rg ѧJ?n72Ѡ5Ȫ;}HM墪tU%^PI}SWժng\Lo޼ZbUl0!X:b\ńlZFe2%VDeB`+9xA0PtD稞TJV'H5G1`$%ñ.FI_wkjZw>){ge rI~(7q  ᫑0R'W Y92ɔ%{b0\q [/XIM[M׎zՁ`\XѷɆ>a:#zWHR]RJVVZu2N g(JwX71(e}*hr#o0\gn C ^\'0]g&ɴj7UmlNH 9$mպٷE_fp@ cbz9=&&ejt ZImYE# xf{QfN@Vy93a\0! zܰz=ڭ?grLN"HV0{FF9 ʸ3-mJƎ"3Cf"\HTнkmW#(j;7b5/޼du9@@RRv zĥwi hICp*k{ +XdcNHI#rA,5#ٗӿg@)9O妖;7sRL|$W"XYu㒄۽2iGg\/p"+ F'rH -7;5:caLȆs{#g f,V4 >qY]OR<u T#J?NR=ljGU[&CEŸ (vqS IC"!\[LɎ\\ /YV6]&%ZXyI3I>q "[ZUF.GgE㥻 s w4ălzZCXt~t齙@A&TP(!6D8CW-Qf;tt3#u^uɇfgjbX7c[r)$`Ba)Ϣ=8Gi/a٩/e#o|g' o}6ݒLCԋieA VKr7g@( NY{Z5A< ̼co`pI^r!v Oߴ  V >8fee|2DI2e),{u\Ok; =k%"8ŚP!t3j;2We'ayiniI6&%%J%FBXvВmF2*Pw2Q/Y"rDaYHaiEFQTw{os&ɳ XtCZHIxumgn 4l+#G͟'0I‰'V?݆Uؽ Ψatpy|JCkv~HlVLrbg(Gc&$֮..q2Z(&<jxX(5p|lOj$/l;Z>u4uQQг5YuTWFT&۰xFJplhzL6Qk_ ڻۤClY_mdfx֛'M!R5 xklC֎޸LdY<Q9=;L& ?>[n!sh40<)WQIvٺ yL-wwŽt~ '{_?$bш~`#DJ# ZƲxɞn.$r}IeZY(;;Z#FI˹ sR؅mۇϔ>>&[6ܚME23d)*#mիCǪ%yJ2BÌWvj0Erψ4mh'arj Ď*b*oeuŲPQ%֦x3U-I;߃Ls)yu7h__\ z0ɂ P> .oqGw0tishrzEIo`qO/!30锞M6˥Jh@~|F$[g4|LwpkfF Txr\n-0 ]W1 df&9L̆Bz:|T2Zt>!J!5jjև}MI}<~+ H@NԪ7s:2$[R@yׂNs,^=R!1&FDkѓ]67RV˽ Tds8 =F=Iݺ+CvR-Wf7ՃkIӠb-l 6q{GKT rmd ax48$ 7Bbڽ`CoZ䘋 mq~KWMT.e@tOYاբrH1˿rr圫".kqNŠE;qfK;fۻNTɨ>Y.~/,:˫J灻 :DNcv<͚gY%YyՎtU7j0Pfa޹Ԯ̉4{-/uO+j?[1s`;]x 1 i!o@ wl$RkŽğ9a,M>x79]4bak沒\¾FZ%RiVUުadQYuƝ"I?>z(3Q6;{4C~N PM~MDo }wzs$.wLyΔ\Wܚ)9 ,.2UL1ɒ0g@olF:\T\5.m7FwA`&.$ejhR[`XρՌE* תjhU\Ɣ OɤbUK4is<:Y=S,)|KK>:|K8!08^w7?`8'Nu8:MUZ3x0ӰՠAf-5(74 I e<>z}\:1 z?m.loZs{/ W8޲`J ` L*G&+fj1򋴌>#@=ȫU 栮O^ |> D2I&i'$.Y2 ᥊CHuVI6,0GKw&NnJ!:A?/aNqQam; `>Ksz[@ce hC]/WmEx.K=$@X GSgو{ͺFiǑHGs~i6N8(@QЮΔ,}U rA?X4noz8v?,KԹ-<^ڠp_lPҖ sdI 2I\.\ VDL;rt;2vsk?I\,g..z&"Cb A:q}5̡j.OKڵ5@دf`9lF Xƈ2xwu?RZ)S! eɪ-?KVft&W0GĹ0Eo<\$&Е\3߇pϞ G}ӐٰWTRy֩?Sʐ$I2M\FZ O'4uj+;8LplH5ѰXԆ)%Xz앁ю@I^E~9n5Qls#Ӥ l-t|S3frvkV <F7P~~YDQV~sZX K\^I/cR%ɐ(W JV+;$h+=;YNe:-FgٮOS &jіLM86I/?*9ɀ9AdvR#iJhH+նj IxHRI#E-ZANN!]p *F.f!RdlEo:=w!Iȏc|dqOUB`#[[Hsg32X2R)@|<H/c]1@65 tg-8|F#bNta5Swz {>5wF*j9{y2ss@ɜNТLu&mXi?NC"gAڎvL6e[k2{*P8\' l-O!Z,jl2#/A}F, oRЎVesPVpbe!S.?E"q7+ŖΣ3O(HҏR.DqVoYyBj(v\{fTV[4$Q;L˘>=a Po*yY H_%4iimǟI42}`8pj0]F=HH2io{;T7 [/=@P`z^H&y%Bܬ6>}< koe089QgauYzxlPkg>,|m H;}h+9NG2 gˎ"^Q,r{wP)&!'YIʀ4]?nʤh'n,1&-LHH,ܮ6 $٤Qb~'Reo92w0i>knt‰=6B,w1I!ڽ$b\ӟ&c' W^nvX.rS%'ʐq&Җ~H4ZٵG -ْ^sڢ0}Bݐ{Y"%~w!: SV9/G3P(Իv"a2xHjcp/p˜%Kz,Z/5o/P5OodZIvmy;cqffEVdXȗ> 7u*n{tT BR2qKK;2=ɾR.^8"J\: >U>#S!I2Q'Z[Rwb'u\ j}|+å닷0z]=e%C)w^ Y~s%ɓyrkKh*4PfGtT]QSn2%Cbdzªm.}:M3I҄"$~pL5D=\sb劚0a1 [Nʤu x#n!U6;Jf"2"̇6F#4I#3o8Ύ2xK<*l ԡP1riY[E |1}za/mvtVV'/ EḙߤauuC2N'W-Z3sp^6\q  $DsJY}oUAۑ24+rj}=v1}\9>GԊC0ReS >t- 8yIZ緷 WɅXI_ :@yV @:-!`vYQ]n q#Du0/x!rh9< ;횪CWNz8h̢@H1m[Ph Y4ޝȣZ$2`X9Mc?Y-Rn]үݢZW (.ۤ񱞾fAI+ z7J 2wp̎$ VtƢ%~@';i ^l [횏v), $B; q8NTϠ`"ʳ,G".'\ W1̛1kR\oqlqB?߹l>:'wy8U^sc+t|nEo47 x>oEF^`i?)x8e%GR`g2Ea"% ÇA0dZ}hG #2DC$ƓoF7W *Yfu8̋RLSߌZpJB&w$7pLPtGDcf e_̑C3=RN$,Wvc^C>ӵ$0$FZm԰&qq !8; GQG:ߤRCptNt/P&[Dgy}:MdtN=zxY5B:wzÞ x7y*wO*O穸I*t'&>?=;R`G}Z[wi!3QFBܱjkm(nI\&e9 }_7IOҞArcX]YB^i?m(j. ypb)GL|t_N[!!klIa'kI@Wcqq>YL57k9V`MWڴ#>B[C-)<MH]#6s^7>;^yan*϶eX{[j 2'GB%M^B< =-2J?V!-@kC}Tta8._A/*Mظ,^j$ Dk" N<7Qm(5eG`\V۸q, Uz]$C!L<ИZ8a# 2^ v>F;IXi d9TJ+]ќƴ!' /#-NN{PQÎjQv֦tjjuk6#f^PO#P śD2j\є#coh3kgw`-}CJ 588}+XՐj.Z Rmy [~UNW:44QUP7<̩9K \jirtc쥄w*$k]z#m$'5V(1U*ieE1U!%x/թ :%[=\L֝Nij z4PYf`sCUZOaHVB0p:Xt!D`g _ :' -xLb$ /,m2p=ʦE\rNS%AV)pn#i6 %ѦKiv¿{Vhͨ5!YPa=I)oNKԥ傒,LP80LqRc ʗ|*OC#oӒ }q˖ &<3 e.=c2ITY̮>td?\9*365o7j T!bgaEɩ2jCާH`y>Ljnjn2uzfϵ؟n/+JzFY9x{N_6,8J)#x12eLWw7;p+H{AOYݰx,7‘@fhSqG,ae Wk C+$WQtNݸq}dع"K8.^^lp]K6hN#/>vn~;dW vH'|h;yiDegf'iOPb ufGd:u-q-QBv\al665W4)QwAƠva-_>zE)capFv|RQW;;%)? [ќ4tb(v2%~D|{ȑ;bV=KOo:TKRxLgv "pHtAOaԸRjK&0TIIZzaXۻ[>IWzP0}5IYWA-N~QSjwp]FAY=![l=6 %m[eyw{\~k(C*"H,k9߻¬lI"fW8E:"i4bhacA:2̲=T/ͦä.ԗ=lZrA`HJu*`Jͧ2GЉ}Iȫ ;TM:wILP AA(%źEj~D JŮz[NPk'/*,KSK! ρ3'5sY<ɸ#˾U&%,DcVCr*rdxdevJzgg@hi@/ӈ;h$r'4H9-/e'm][yy{N /׊J.Z533Y g+\G{棡:-/viqnH^²Mg/x;f4j#`j^.֪< Tdh-}n<Ӿb{h}WQ8νNH{v-[ &4uRe0;w.)N&x?~rN>=|k=s?d?ɬYeR0wizl|45[r46fdM!e@{Ļ@1h`_J-].NX;#C$q_ /Rʙ>L)f RbC ZBOw*OzޝuA`\o(Pj>aulW[%G,P2>Jh~ EG?/H24L̞ZEsY">))>ځbݥE}s-',I&?w^_}[5z^Ny)~ $wI]OM/|룼E&*EP_pRN:)HoBtJ = 甛"=^ xJ˰4/]yEQEUˇbϻuIt]|3x vd M{uuhq< aO" E=U*֣Zj_^9.[Yw4azarITr=xfi7$~/B=peU)U_uWLA ]jziϮ`΋IA]"% 뛌ם,5!OK~v;hsKehjL L' 6xwb=@0r=j-^Kp衚TKfN4PD&p:kڇF ^z%LBB_)+~ɈDg?tp~~TyڐxIL{0޺\cH 'ː,>ى3T_֑[H?rYYN=~;S&>?N+e3L\G)z{X:HHsޛ5h l+ YI5x4,NE'1:\ ̗'̡,$BG[LB[P&fS cBfSU:!J*:uIk}Vl*w,Q{M$l,IYS6Kn~k^&'/7Ȣ}HL sB\u&+ct8S12=pJG05B]2 6Ǭu t~XtCCЎ Q[4v5<=gFb k,>#Cr)NWYWjlO8V#.r]41Dh pEO|m2(Ne R4,O-wQs17bG r /&ÙNq$}z\3=$-C5J3\3ǩ(Ȉd*8MKpD[:Jyܖ ~!(GezZ:'PfzY婢Hz]9? } H݂alަ=uu[òI sʫMww -y:kZ"(Y9.S\MTl>w#H pAfa](4~W 衮@h>>CN?#ݟ}TMEqyƞW0z'WbR?X9py%Pyw̓.`=L&&H؝A+[tPtd|Z<4=;`y-Ĵ# l.X޹SE[Xi7&qc`Pq,ocS^7c7<ifZo0::U|Tǒ߮" d#~4juRuiU%@,*zO8%&mR?~WQg.fݱGzfd~KnAZ)wcWz^9v M/q>H04ԙF,#\xFy4C{[ЎH&L@&[/$|P]Kx]5C:e䠹~jC -=ծHU%iD^ەɘߪ=镼ߜO{:-#F$+@ՠ>%~{K&:5"&=2;/͊>Aa,$:U^rDv Ui G]55< '=5Ou*r,'t8D6ϑ3%_U֦Vll!ȸ$b ^U5|>V->e\t1]=r3V?W! 6gB?.*&+&~a! ͿtPMOR-g+ny3[قJ'߹tJp_ aWh/^{s˷<_}lP*#a%#iT0Df}*6NI0L$pӫh zhǎ~+i8:U7>~Zma-FOdKZ.x 71ldӪ$Z*;uA.Wμ I"h.K7J4j8SoijpVzJ7T*^\c0@Pm9eL!'|V^W*2w0f([$n|!<Ɣ?e:WfP8s &Ad(x20PI>{$'~Vu@uʳ Ո$=ȵUj|vucp-].٩+xqY~Ky.#6[i6F 3c\pP$FvE?ԄQ6^ec%IMab'7f˷Hv}zn+N`#riqQH:hX4>=ҬJnW;'ur`0VQE<CK>ʞVx1P1C;۳_.x$H['JJٖ>!a4Pº߇CdU+} qB2"ze 1RC8[+S9ױ n^[P/ G'K5-qL wm<{{f>)sncAoMK=ӨN75۟e?#Ah2C=pD-:Kgj3"wc>CCa6tIcM=Bgh0pp&St>^M10BڹbriP3yLvN5<_9 o0־s/vS0Ñ)Av,?p͜R.6n4FqH!&5n+Q'Rjp W(\Ž>zvuWREf2g7VTgX?>ǕqEFw3?y/U|lD Jmoڣc|W6Ҹ+Z.þzIpS3Rv>sp,nQ"7=Az_B>q/{sYc!ͫ70ċ~)"6EVY&TDșZq/z^5vgvOϝ#&WlBnplkI*w$21ed!PAא|lR~(]Oki\aX Wcbc9Qtiwn \O1^;`a[7é?,05c>;^.ϙ1^Azpfs{#+Us̄CϦ~AI% O#B\ѨWCO!SFݼ!5x+ ٍs8 v 28;iRAT}=7r\8HR)k۟H桽@vaAsGJۯK} > 5b;GP/FA=6V^4ʘjhƫ~D܀u%@&#w۝`z#! ^Ш0{H)TZfUo/kMAz()1;ݓm+N.krM&5ޣZ#"܊Szk#TyLJxתqSWpjX@TB[zҏҔOixP_JbBcq93ػx[`dG4){ ȶxB$es~r@ T?Y>] bY!Sl0DĒB~^4/sgɝsj:\+UpRI]|?/N_]^(:Q:vpxA/s~E6rK{:C2&K Q.aoZ-c^Xe0SR1'70y^jBQb ɶ\X4ߣz4"=s>I{3,z?afRU6^ڭitʪ15ԠI,P$;V]=lQ8ɳo| {g}{qF]G'^{!Yb o4GD?M͙Ӫԃ蔭;bgn|j椢c9$>PN\JT,7P4C/B)7Xa+Zk/TҮw,T%̆!/~zF^#}g>fd)l*Sۙd{&u8=w| ~{RP<^d<:[idRO{gC!P/6I\ѡlq"&TP 뻇clnEB5 V(3 "+Wޝ_R Cl{.k$Ȯa2pC9BFLmѽ)҈0؏4 j4![hYRg\,t9fCD;ĜyYG %&e/,(쥽)!+&=vQ~V2$t@8(|Fh'9(M̵$ 7`<d4YI<EyCI n$nҶߏjT7%0&j}SփǯjajCΎab:N"@5C@ݫ[gwkug#^ad(VCuEJQ{KXw2J3Z5;rً;$<cGK53vR٩! p?M Ic|>w"1i\濰 !҆ \oC ̠YΚX%X~4ӓ6pR]N y.9B݌zˑzjN+'e3V 4H|-"L蓭r~5.NFOd`&Y[{"iLԴ~ T ٽ#QXKT~ŴX.3} }O3q2DC0UԴ f9΃GNT79Z#ќRG0tc~gdZ >{wQ͐b *7X5GF'j!-\բRSyiUt@cYz~}~Ci!4 ס( ;ѧ&=g.zzʻ3_$JaP=۽MEó0hu=)[DyΤ+āOΏVXKv{޺8YjzUSv2hQ֑0k.DX }|a1Лuǽ55Iԙdnp%]z=yq?SQ?N I(&~{cs-BoRx7JmHx;smD\&.QI},IFGz1_xA5 gˉUi+q5g~g2d.Qt5hK $덽K׈.Ji!{LKu\ ZVU#eA~ctqqA)DXVHgIcz,f5 yeԣO'(1ǡ(GG! "lgl~1v+\6s ]ej5}h(:&I8at|b 2#TG ;V{o[ٛ ,'>l Z#4#za\qq{xo%)1-1UPQ chGe/#qFr^(ΰΏC? fA);s8I(kn"2hηVp"GCL!%&Sop!C_Ľ,^=>yq7(}]/VKм'׮;Y<_4rլ͗Eu ͶSoƲR4:/` ׭VK`sV\jV/bd#gy?wAV4V;R4> GYt7_oTF_;'%)/PY}"BjrQZ"E jd O6iWX9}3_) n.FvD^LmaaPW~= 6M$$x_3k:OCsȻO@0#:ɏ_-8 fvLIp*S8wj;aAnu[@gavPɫ,$n{{fA%L<MOC#8{:L%ήP{R3/@`X Q ۤ򯞹U_3 B"ǒ3Lb 5WW gIfqo7:R 5NE!麯2hk \,>۔4?l_LGQY|-wW:.k AAs`:`;[_̞'M3#ur/D@M0}}w>{e$c*5K İ}B>}jp\A:24+ r<qi(.Kw 0pH%1byo r@bfY((]+edN7$>f10mQDsCfF;1z< l/u7нX] 3:;&/ #doh aàNLj0_g*Z-!`__4i$gGw U!_3B3oCd]6-s8To碜 5 eX{@G<tdN%MG2HdTҝvs^!C֤TTot)ʝ_F}cG)GPgz5Hpg斤og(XM_,UNVO=[y 5;,%dG%dG&sFo$tWJ{ؔ? @M?͇'eO"Y4H{L@V,-Uۖ'-RLJZ<$*ߧz^~u>;o4* ЃZUDG*}jZfeX-2ݞiV"$ 16YEU$5(W[;ܔDAӤW4v2%3`w1޹@}!#1A9C&.=o!&͵'Lsd=!)DYx|A23_BV6{_|OI3#^_W n,&g|~W+rxj??]bw$t%٭)HNp TdM+:4J afc3UVR짞9M eQ̉"1c_ߙOl5@@ji`b"I;gj'Eo)Pᓴ1HBu;iid1~>:.s[_c+/P#]BQ2H'P/ UN Me?z&gڂ^t[avW'(kJmn˲>%wbGg%?:j/{S}Oۭ}e{eK~׏;Ё]w )SG8,ow\y{};7K/,_×^g/rݟީpg#1֍[\K!)e u38 ;J􏶪"$e+Ο~%e2ŗjQ+_տ_tӯMԗ_I/yU|͐xA EU /3 {wbh]ps0"~aPsI?? }?KsiB6}. *g@h9]tW_T 5AK߮8w .|4/iΗ I _F{7k9 3/($C]I:*CO>ƒyӻYLFkT)Ub9fpz5,V<, A}бaF>=? Q~7o0=r܊HvDoL22*QI>=a@>'uga{pb, *jgۥf&(_;w6^Tj$3N_Ԭ!Qrx!z[o\=d0r`@ZA<9H">! pI4X$lAѹs_[~տ_dKK.M|7/{ăk'Η^E/]9_p<(V:3Q3ۯ1/T-SW\̿F5ODZx7bjDzQ]V..@|spXPI$cpOVшVQ?&-vK,!ܱa ̡Ǵ ytN s+oz$]e܍ń٫1 Zѩ|=l}f¦UDYQK~A FXݪ~I@.so3F|`: :sE#̠nf̴JA[5g|U' k|-2xlgp8M@͟ OT48Ivs/&mr),R)[e:yǙf(aoqbRؙ;vj_@a6#1ϸ6}RP%fqPV¡Yf&]ӑLIMUAg mG8:NϘr"$}#:7S D?8oc w!; 'c0.~AdVoG1Ho `_/<gzUXS%\v%^J 4I;`}p=L^_kw SJ?SJnPZޑEKE)D$BㄵB4d*Ӳ<_C/B&ؐʙx2G1v^&l\Ac̋#EH2G*/> . &#onxn8sIGXx!A̯ͫl _k8Nzkg[Y 58*M{DUK)#.L~/!@ǚ™I?="L?Z4?DQ_ݴυ ǃ! dWDs]G[MgzhП)>˹xнx%\k& YB8D!BkTU6v1?Fowl 31C{Q}i$EPG 1H-Holv_#6/e|#g2NRd dsJVRFǬ]7gW#Vq-TvSPOvo /f__Vx$Jԕ%ݝ%qA^HU>