From 93a6a446026b6ecd2175007d01809d7f462a0569 Mon Sep 17 00:00:00 2001 From: funshine Date: Tue, 18 Nov 2014 01:24:49 +0800 Subject: [PATCH] bug fix for net.socket.close(), add node.input node.output api --- 0.9.2/512k-flash/nodemcu_512k.bin | Bin 520192 -> 520192 bytes API.html | 2241 +++++++++++++++++++++++++++++ API.md | 1705 ++++++++++++++++++++++ README.html | 1126 --------------- README.md | 5 +- 5 files changed, 3949 insertions(+), 1128 deletions(-) create mode 100644 API.html create mode 100644 API.md delete mode 100644 README.html diff --git a/0.9.2/512k-flash/nodemcu_512k.bin b/0.9.2/512k-flash/nodemcu_512k.bin index 4e4449ec8614be5ff094d4bc35577b52aab31e85..3633e36950d208f34b0272a81b2edae66ae75690 100644 GIT binary patch delta 51585 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 delta 56971 zcmaI83tUvi7dU=r_Q3*omt8f7|0@M~L4;i|Tn3BQ(&6`jV?CEEbs#`l*Rh7|+3v4}J2+XQnV>s{HPv5K)( zqC=KgsVr8;)Mm1pXoMaJ6$~Rw_O4XRTbS9W_?6OOw(vjNVvIFyF(wUX@^=I1%bBio zoasEznWCyRCU%#`#N8M4_XO|C7HnnEeJVs#$e_FQg=-P?EdpwFz26YfZTiyw{|xV5 z=#~q0{cpc7KrU8fE__#VOOPS&N+oC^Vb~tl>3o#iGPUHeFe$ICMpe&sCSE_&7E|ZP zFid@0Ov@Smid!jmmh&5Av;8H-Le8JmDBNBlnnn9*F*?@1i|^|`5-aohsqVee4t|mQ zAgLJgRwS2gcb|l?%#+8S15r4y^BjOC^Dn{w8T?0{K{&sjFY?rQ>Z873w z(3)GJaY0N4;1x@Gg?uEg+fp`OzFQ<#wpq{dNHxp@wT+hDdO17T`V$|kN)}&xX5GuL zRb`2fKC|*=0p4y%ob$|@T-M(w5BW%zN@SbaNH>Ght-xQK747BBD|7nBA|L0w64~m` zgpAf`FZ=stz5FByJKyBhJp+?X&22GyK`@9I*1LQ$VlmWkF3?z?c#L+h?WErKjR1f6HN$AbPb_~s3i$FJ!5Jo<<~+VgYtQrS%ZK!kqf zm-Na&d&*GnGK6aRy#ZmUl5Y$cf@bmlfof#sBLlHyE+}N^TFj z$dA(eg2wYcK{HVV|6$PIpx?~kzP-jjY|mxJs{XzzuKcOK{HgiNHk80`3Vsd zkSD*o-)em2L0NGBe1x+3y#w;mR6bs7=#~87e{z5KME~6r^H;TK9KTvS0LAj(X-9Kk zb=VdiRh{LI;R_l1w%a12Lx?(?@pQqg&S{6PPJ-)I_G*~qGgRQP@A$wfcW zM+4hg^h;URz;}=||5{s&I)T4GXl&q;>(FZ$=5cLUhu2f>k_`_p;L5XnYUms?T$Cy$N2bq>QgG|aAct-K(!uH|o_xLq~pY;3m zE@alR&bQiX3lL9{j8>_NsR&g|1~KZB>PbZmTEXuL?~fMqzlRU^T|ikly#L%i%XAoYoVl8s`3+IU?|2+UOpO2aTe!Dn1FBy zPAHz@(QGJY#b_h{d!!x>Q&Cn61j#%3_ zA5?+>5UwfKU>e?_-mZ5syw@$`y`Mjh$48Z2e*P8gy_p9OwA~l^W#Sj zMaTIiBV)jQ50A`1C1tTOcM#5R<%h*iz|I3@xv{wj$2IfbqxO4HBR4|+s1^L_Q9)q& z$D>}s%sqZmoB^xN{Ia-V&`~SnR-yoYg5@p_zQ@PMKj@Wqb3&?e3OYaE`r6Hzthdg~ zGWJ>40byP$KWX#=G?M>$^jO=Qx7sVq{oSU&-e&%C1bU;BaiFx;Fg@po~Xjy*o*@ZTeau zy@2A&wj^X>&#!N`>xFLI;0@yjp+EVl5HaNLUkWz#*6*5*{mpV30mV~OmQ);pp3!57>r(^gd87c#_OGo zOI?f!F2-!i7y*nC$U+J6?#zsLHB=&d7}q7AFWA%*b1~XYfSwmW3097$ea0;aQj15%_2n%eYecNI3E6 zZ~oE?4m=^5-!P#cmK-aqoFGEz$1-Q~RD|B*gJ0AlYgy8ZeG%%#&z=|w0b|QVDMm~9 zos;zF{jxtMX)wOk%!{VHiB6TxnG!C-77xBKbr80&{IS%Lz3n1o;QDE-!!_1n1)N&P z=I7rnuxgxA#P@r3yvQy={Cls?>FK=37&w28RjIKKt}xv*Tm3Yg*7Asd^6HB{Ew|d! z^crh;h3T%@+Ec^za<=ksOf_L=Gyl!h)LxQCrj*l$+}2n_t2lpcWi(q{eDAvxmaBZ= zYvcXx7Z{B-%)n_iR$X}bT@B|Gc`2H8Ht^Z6nR`3WFcnd1jn!LYHJG^`P^`&SzT|iQ z;%kY$?I+rkBQ(|_uH@b(mkQ2PeB89l*jdSIty=8-kx#M4^pYF^P5VG8php4c-%;7# zmP7n@YaDid&$n3T_K@siLMk=ZehuOG3|6I1Zs2^JCH#NWhWgmIF%1oOHP!(dYk#2X z2sjGu*!5V8&G^^oM zme2TeuSfbyc!;RfCfWw(9;QXv*YX3V$NN}Tw3jnbV-2Ahd?l;PGN<=N*zy5i_(nf$ z&)|=|Vd~|47i!ZNvV%qiT(6GW1WMlL)iYwT{XPEm8NUYD-vB1xD$bk1s+I|NQ>-eT zoT*hGy<~ZfPoBwnJFN_JSp_UQw&8~QfqNfu^OYQaEo7*JIjC>M6HVtbX<}{I}_0 zy)EOIrV>V@!kkYut7g<1&d)syTZ1JQ{!aQlzr3;(%mip&_7!^$kvh^vc=Ft@0k=qs{TiO;g z9RO4a7SqW#pEYkTKW(wNZ0@{?B0~if+bt*a64T^OKn@sLjVTKlL4>* zN&sH~s1y7#Ot3ZB)E(*o?*t51L>;y3Vp0KUI&Hbb+xV&v#wzHV z>?y3zS^yrN;d_6mv5BFYEPyY78Xy$F2oMJ_0U#A%I>1~2Dvhpj8dqveTX(~fL837g zRsuaiV=4yx{D2_SK6vJvf=mbD*%BXQIt)+t`5;pbJR1fDnQGw~Y7R2h!Lu$p$Y#p_ z5!PM7K_)7k{!xL2d|S-q5@1*ZRRYFh0szm#4Q(;BfXvU^VrT(Ma1dHR@y50oT7c=Z zwisG~auejGPvE2S8`gJuhZM^2hxOvtXPimI@Y(P9uz-cOaV8l&6Zt6_LzGH*ix6u} ziQfVr(wM+AxU%mv1|wT>DQEyt0Z18!aT$~f5D1_J2nUD&FaksYm;mAc z5&#kbCICzXNClV%FdZNrU^c)4fJ}f4fLwt5vbLTv>)@pjU$v>{#i8o(!ZD{v#lyD3}<`1Nl2w*tPf8@>bZ^WEeb!Qj+YXis4nKIfe< z8?E=fLZ9;OUdP()|HvyWwiUYr5fDz$d=k#UBp%y7qL1 z%kV}Zg#HH@z;AqPllMdO0!#;(3y=wr2S6R2I{BIoS|L2Q0u%$dD%9~Gtz|t(q)yui z&+7np0iFVgftLmF1qcKP1_%X+0EhyJ+uvr3nE)@{1yUQu9fYR&q^k~zfCn$>!czfP zc1xcQIGfd#J{$16i@WdzfPa}@1aSTcHv^czv`y2`UhxEu%N25JF>tarWssbp$2hUfCzvn0NTn2muXC( zt?Q3Ak}u?lTG3U+T@bk-uM4L#YP+Qe0{@cbUFpGq=XOgE1$;+4&M$sPrI~mLssu0{ zU^c)4fDC|KfHeSxhxqY}N7}YlKsJCq0Q&$c0BQgxfI7ACqz-%-p0&^<>Rr$bfY$+j zeh)MueF8KBBmn<)c-{qg3a}2U%s?j)1IPea03|>mKrlc!09fG#*HDMyEusqI3jj3` z#S`FN+2P!s_`U=Go1XYD{%O@vC%@F-T^f^kJ=CEinGUMcf#wUe$v~r%94d0pZjC7z zXz?O&4AR>C@Zs_CQnz1b>TzP=+1S5JA`5sNjOv{lQ4N=L!+jw=vtL(wAmCJa9Re%b+iC25a96- zLwGj^nr`e&cXbj?08`~T(5>g zyKztnd%EGwacHM*I1447?}jsgw{*j4iFw^{T4MOdjuMk-iN26S+l?a_@P*xQBj9xA z*x7PXfUCRXF!s`Ema7i0Qi(KjOoW+Try(aooo08#Qvu)D4WAD9zHa!&IvBU2yYkP5 z^ah&#KTY4#je}Zg;mEEW)D`x1!>KFCV!F}`L1J7td*OKA8P5s&jW7ihBpB| zu^WCD@M+!hKLtFI;?z#APDM-D_pclqyWuoPF2(<`tQb~Z>7%-IU;*FS4fh3nF0BQ$ zGi_@%;1S)@Ljj+*slBh$^l-rIy5SLkclLXl9tC(uT6YKcUR9Oo4EPoi{IUjZY8hXQ~kQGlfh0nTD#Bxk_J#=}wajqYc&j+%Yrt%>TL^q|BczRb#Kji=lwa% z>+j5egGzl*&oHmU^YsPM5#jAm`e5e2vEaY+=cwOZFn`vZnIoc-Vkf^gA$CgQ3$byp zy*TC-3lj=FQ2-;KhrI7t=h8eQ1`lTbJAYQ#>uT$}@4hjA0q4OmF+mIi|CqNIy;in( z$M>SL3B@M1k117Y+70VSMGMOG$@5;J0uFxwDzSy%c`!gb;SHr}F6Agjnese#h386- zRql`~`xOk5(!Rh1^g`L~gW=I@kXTyx4Or)!Pd!kYobC+E0O+p&SD!9I0hkQS6K<7LY8qIP|f^*zp7VEFVb_8mo$8D@Px=No;_t45qf@Bfp{xiaU zT34g$Jb()sCB!5EWSWJTZvm#n5;!B-j%B}+YJ|2(eWCEstz+`Ygf`PrCax4E%>A7 z!a&!WDHq6i_=5oF#N?(J<-|^hv?wWOS_651hIhzZWyKmRDHshmzkVC|NNLL`;C1ormX#zmgGBr15ANR6Ad( zQcErkA~U2YAGZ!752Z+p8VKix7UR3IWQ!XbsW=E4)B-F3W7TaXt!^jTX{^w`RhwCEMy$qVyBcC;QJ~?Qu>OIH{-Np_Q7Wf6!ntO!6f+ia1gP)a zG`PzdU@~))8o^#L*s+^Ma2UG8Ov>eG1P&iXTHz_xgR4x7B?bj5l1>AI7)OzF3iKFH z+(u4&q5XJCJSkA35U;i&thbD7Kk8;8EaWF8T7a8}5R(eU%Djfeiy6xz16is<%e~bg zG8jM$Fqc*}mh|^VlkmV%|f0Vfj#U!WaDqYt1CA2ik>d$b}wgIL;kH z{QOV>Uic>2?uXL+lwc-b0Dpi$05w4HuMSO5Gy>sgv1F=0GP~{&tlLJm_@gj%o&4sH zX5z0_IY#zEGbDZyy@O5Dp>8I)5wH~$qU~~Un`3`p^Z`N#o#NF&@FrcRh zZ+**gF#?rh9H(#;3`g@3t~*1dk?10BI^(z!i8M$`x2TwUhvIoO&<)Kdk!JJ)zJ7)* zGehE2veOJ+`tS@fj6&NbOg>DD$)!ivzPt^Fcp#zGGKBx-anyhjiCrSfQ34 zgflYO1>19m>`z4Rh%94Fj?g4DU4q5+q#y;F?Cu$d--~F27+rUiyo|i$BIhq7$&b^K zUSfoN#g0eQ(KC_Ao;T9*C>`xXBIn$Z-|Tr4A(4IBNaA=4>2Op%x$+h&m&-hrrf`7C z02z*Lv(euOC)7LE&OuHjviOa3Or48)XQAqQl=#1^;oE?0t_?*L#gK}WxJLlN{2|^N)<*g`kC=Wd^a;8U-r+H|j$nt6w z`D_JB!ssy=R^PRcHrRU^v?}`q!$1AX71R*6GU_Vz{USHDdV&2N1G!C* zKGZVXB_Q4lw$ho*AXT`g!caIJ9XtoU8~BVWOQgZ60(laPfs9{=Mukg~Tsf-U=^Ym% zXBlEJqS$SMRy8&eiZ{do&1p2ik@DZdF*uMhkjizar_?#gV3!%l#dRo9bW~Y_Zu$^)CDTybm}n&@5)T* zH61j2jh>XON4=%aOM1%*Jvp%+1t!`5&`W;Nv%W^eQg*d?v5t|8TpkcLO?zcTaSbenxxvsqMu4Ir><79rkpij*;rmQD2S4^e~;%vHJT$ zlGK79>R3z6!|uWL?sg*GgvLvKVUZvBEqP@VYQ@@b$@nkOTAcVTx$*@Xp-6?ai2$Is3pd^(!Nh{O2&4pQ_zdIh)aAZ_2H z@i=fN8Gi_#rk##WhtM1>od6pJlXp72E71lB8A`{lDzsmOjWy)WY7{o`C$A7WD^?#~ ztYf>mq1MM)>*Z&D1~<CB?_9`e0A_cvR3Q>`j(W;z3ddYErjAs5jr3zpkLypoYrc=g8~SH0b|s`#f=BbIT8!%yU_^n$A#hTY`U5!4fx zcsXtyfyj;b?Ia%`MSVmP`#r~|qtr~-cRG6ij69Hn9``&2#l^6>lvqs+wdfTOx-5_Z zuH5BVTZ>XexVXS^?HBZu2pWr&|BAxA=~fhN9wR)p0O7kF_kTs3kkkao^j&1bZ)iTw z+(i_pQD2<5i-es<2I*IjR^w?CIDEIG-~#Fo?X}ynzX7}wC+;SXFF~|ju$$yuMu+g$ zosRfF(Fh5B$!zz%?Q0~u2;z^B_Tq*W%(mj^j#vO@wRq zIQIJjLD~qc4SUF>p7;=E_7XpTd|4W`7aVmjY4gYT@#MXZ`@Jwmc=le$uEtn=$zcw|&=?Sh-ZS7U*w~Xy9fCi=iLPfa za%TuWiuaV0LlL+L*OrsCp|~8MFDJc+;Ys*uIhj8U55v9=vV9mHA)VlWc6N|!!|(?^ z#0sUUQLZ%I1@MLU2!K^Iq!~sm-N4Ce& z+V3K7T0kcwIQg1=j_nqlf^i}5Xd6u(XWu?Y*cjYfBrRS8!^J+w_(ZI5!wvf!Q(wfx zMA-BlSvv`b;fdclswYvSXM9IazYG$fod-_FW`y^A=a@4E_r|#RQ^&IZU=4`ePj;o^ zf%w#ZaxN7caN~ZWconzdmi-RJR2a+f)BTRp*YJB-%0l-DJV3(IFbtCih~{K#+w!af);IN+G`Hr|e; zd60SI0Y~3=@JOUM2*?hAMgZ|a$D4EUST6-VlrRCz27uwB%7)(vn~uYXUxv!S)rha8u)@i62;4-(YtV7a-@p;-c>hI9uIY7UX{Ibf5P zL!>$f7f2rh&3`AE`U%vW{ef)x1iViBgJWzin8Z5@dh=uoFt*b3g@hkS+ETn7Py2x= zmf<1~W-WvWpy&QT_AkR#(tLQ&CnS40j`#Qq-VXyb{NOmb9M6E(_<@XAfiH*o!j5+# zfl}d_3ujDG0BU$=;YrV!wD3+()|7Dm5?bLHyAp3g*jVAXwhDR)o>)O<6yRmFySEl# z2n`D>94o(|9+p=@4i)109>z+DR|U|pm1M+byiD2zgGfRp`Dru$2~VzctS!Rhkz@fd z)sf~e@qeVb@S0cY82c4YK^_%=Yz4@#bZq$=d`Q{|$iqs<_;0{DJ$&ITg2wdBb&i~E zFsHV)&o%958GAg_KHZeJ%+2c9WT-P(#b&D{#VVaOZ&8-}YSczxGHA5MJ`mF9EzDY% z9GdwmPMoZbU8-{DmakurEV~%lYVXQ$c}qC2_O7frX=M$Co>Q_QyVZU3(URs9>sQ~v z$HY3Zxl$=v!(6c8qse{+Vr^K>cr7Ta48Y%bOTJM`;^oXY`G%U%%R8U$*r5%CjRYtd zBPCq$sACGRF=ln<=mJ(7Xi(dbXdR>-#8shqQq(gI=WgI+3$5wNi7&C@G29dtD_%Z> zmCQov^Xy+SH6`_xO($fVy(>*{cZ>D29dQHcN2zo_{8Y>8j~z$|v^>|6aYxJA58qmW zo07Hc@|)LX;OSr7YDU`C#w@71m6c?)migxvS)l$y+86!O}*xL0?@|n3dEdXFM(~T=Jc28@Ign zD6+3-q`%U+&NOJZe@xnHRj_59Mr}TEv}FD2WB5k9QJo(%7cjMGs2M4>xF#_GkM@>~ zc3E^ZwPhBb z+n&Wpj|l&2C083QKYkR^cCy%*oJ0TSSgv5@iLX6^3()S!@(~kXE-+vHLATzZOF@4U zU$(ltThC@4wavRAJ?4gkhb?bBKNs99Ia)%!Hl;9=IxZM^5t9?hSZ@ny{Y8^bi}kmJ zl)_UJ;xaWs*f`2Lo#Fl#v>Mc#nws?qNQu2FaIpucL_|(Rlhy!@8+lMa@?h*G0ZnwF zBMzpDKx_|`Owo!AwXN=L^<|isCmUmFacoDeE%TY0dG%RMt7TSKZ-z~dOC8$NfH1|{ z9uF+}e;KU{v!JIju@8mxEc>o+TsoT`fEZGi>iME+{Fo$E0j`6DfMBVwe@nyzokzCD~C0M6_Oih@^_GI zV{~3d;DGcb_S_Jo586XBX~WKGwBE=`ix_tyAI2 zN|W!CbF9i-331jobBeE+6-u^!8shT)n<2_F*!;mJ73h`*C8{H%HExMT{xl z*KB5H_-YG8j4gkSZ-E(Q!vGoCL(^Ub0(nDd*(DI!sdSrQMv9jv2Q&CBDW zvoVvI>06kq${xiOV3eQlTd`i1pR0DEn2pQNk7&o{W6}IkC=H9#M!_UZk}^s}<*aeZ zF^DjmQ~NF}inQTKZ>fYCKFn*}yYCP6i1Z$}WGQA{tV49|dnhX~jFI%7Jr?0(qH*d0 zd&O))jvKQv-{{X4x%tqYsl2*z!A4mUg94~MFpG7}Kbsx<#E^f5r=ODzK}DVnd%7?` zqVTJTnHyC1`(ay-j$t)Lo+x1X@7tv;!(JY+q0jxHxOxCHXt~A{GT=;&O1)jJ*(@Kp zoi)URq3+MzAZ1HkJ2$L1d*=Q1=756y`~_s_>;f4I$o+ji+yQ=N(6T83FTGqUW#_vX z1GMvfn0;vb`|AgV1k4}Dr1`)`+x8h#Y~r*R>86pqg}pL!y?W66xpNo1KQve)Lj^Kg z@}OMxdRN(0sPviug|GjT&2GAhXn zxvjdzwI|{UqFMKXIHm|I-O-K@SSGv5_amI*=KJ&e!#|ZXvc&-hN?oa-T5X~2=iGqx z-$XV5B6rt;p*xzCYIu|jLC3@izV503v0E8+dNE^U(d(arizgssAdANi(TrkhxQ?6m zkf-6O>QSsaicCJsg;<;QI`Iv0y~t=yk~T6)s{E?y_`^I?xX**p2rhkxM^y|rBpGcQFW)3~f~Ep?USE~lFAK(Z5^Rw3rz#zb zVyP|$g;F*z#mhIr_OtNQVbg_*0A_gjzIrPT8&-F|;$YpwWDng#uK>+}ACzoCy9NJQ zoY(?FGg{!3t9?3xbW|SX^N}4(T&#I4!3P$0AQOXM#LX=JtqME!KVv#Wm zC!)Mxm)k#=Z%P`$5zR zw2a2en61btpLa#r@p=mEDGy6a^iAk9;ideFmkP(cp<$J3O@4)@FmgU-l>rRgaKed7 zLm%<`aD99slb>I)zA$@?uU3K12sW^{QDJ74Bd{qhzap+MWWm0^fT|BvwBwP}-4);U zEdn{)ixQQSqx1f&Q$(`~NpN9(@~e6OO?aE4_K6V9Caco37NYsHho;RQHbv1M7&>eN zE0N}sN0lM-##qm8KDxT{(lhrgS>OecpW5bTgwsLM@PahhcPxWNiKSNXOOfP;79gce zMwH?J)9Cf_Ta+VMFR++oO7deZ%nN>`v!{fx(FLK}P-EZ6bgIxqN#{$)2|wR7Cg+9* z43Wtqlih-T0XbB}h{=ghUrL`{RqH#c`k{87(KXqJNvy4KNt#?dUoKg`vwbe>{2jjG zsaajWxvAt~r7X*}PBG4#Y}K(za^RE&0xy)5bH5{qpwhj7qHIAkp|khq!PIIE0JQ(3 zWOo&fg3YlPM0DM?!+Yahofy8(IgBo?hkQqENdI5KkSf+Fn9w`J3q~DN#E*y1;~)?n zDfYO*PDV^(g}Y_U(2cq@1rzn){k5I}D?N9vL#%w;l%=yWp0K!X5dW{CzOq5sxT2M1 zHvR!p(T^9PoCgJ-0kr`)Jug&06d)xpCZiR;XWrOHV*`%;l%uNf-6I7e%2Iivd-k&b zd-lummxW`BsNH@#F;+0Cr33Q)Q_ln_ZZLi;Jm4gI?x+gC1?~a0o)@G~gpD^eEE9U~ zfp^cBy?vwZ&-C^}o2XPxBI9Yh5KtTcKseI(-CWd=QPJ$bNapu>YXQqVSRWC<9%F7W zo)_|t6|qdwPj&YqK)Gpwrn#so%bw@VcG@=_Ueo^fA{Y^8=m=B+r zbohFw0Ke$J)8ONZ>Po*Y*8*xmqr9Z|d3+>aoN>}tT`YKBVDc)~p@3TVUQ6Ap{}4ha zdk*O@8af{{DHwf1G!v#p6ku%lv2BoM<{Rj<85QrT@~1`2oCU9Mep3|3_+hC5WMG34iwT3edsTiSYkEQfFY5go$2yLZb z(KF3@moY^bV4Yptc-vX7{{d#ll3Rc2yqtrsu)+7EP!g+?>svcMgZC>E>*VkW(N*CY zUVB+2>#J2hFbt0dmIOv}S=jR2poM)WE4I4X3M9(ytMb?9Pgq~LZPuej={=XawaloP z)zd6d2E>^yN@G~SkjSuqH3P$Jg(i^wpfR!iKZ5CL-O={X8#P z;?5=C7wih=XAZ7(Bq7OlLCdkQVCu=1X;>u#11bb*o2JlUmT9>FW`Mf6W^>2p4VY>N z6u|m*7e4)8!XF4u85MpJgj=rsBm7R6@c)-=wOI|VdD1G@{AlY_WrYFim}rd3`OA$9 zct^HTmBebQ0z(i=;=xCw*`IVQY@uLtpcYxmgwq8K?5lj84@siIA> z8LVguH%spxd)9h189dVsy;5F#L_ZPyL~`mc?&Wfciu%b*<@y%{o8;HOxD@IrPOmGn z*prE3BYel6fF|qHxmlr8qQ)eKq(;J#R=u?*xw90oPKC=iT&sd(ct@I%O-NxGt=T6(L=$`8;4YLuuC&F|B)|QF?EDf}Yv(2p7fSGi5G|#590h*9R z&l$7WYC(`=ZR*U@0cPmitk|6!-7^q|nkaOc3adSt4qxbMQv=|utB};3dqO%pDd#Z@ z>z2sG$kghqFcA!YU9FxER;CBZI&rjHlGM552H|$$zIf9O61xlgN!H!4uew1}cVYh# zOqIrTzEWd42%v;nMCPAxjM3N@1KYVUbYd&(Tzi9MLbB%F6Tqhon;GjJA@-h-rCmdI z?ZSzD@^4sH-Z+N2hk|njG~y9M56{}FS_B)!&c!zzJ$GX}k`{wQ?W-b1#dx`aq3io- zFC7~yMsw-Fsf{wuMk`jq8!M7!gycO$T2+!)$n}BH*zV`i-OtEtB{%@vR*{SnybmYs zBg0DJ=w!q`l3j`?cH*rLN6j8ALwGDtPVR*h6_bO! zS&mJ3)CIDm91p_UmE>$W2W-UwR}mg$uH3fCzvD zfK&i*h@<-Ug`PVn%f0~RprXCxGRXDXkO#Vgp3!XcJVf$HpYL(1S0*Kftd3@B1v2tT z?)O-28(ymaPDnUm|GANiD7DD`f@N849j7nV?-eXRHFASXC2oIld-(wyeYnt4*t~Pr zG;#w=osz#~m*6OPQX=B|m+E&2_9Km4aH&Q77v>c49?XN;Jveo#{u@D3-N^MVbz)$L zMGNeM1(fQG1pDDeu2-oY{UsZCDWN3bW&qO=KGFTsptvz5lU{G-yi4^P1WQ#Tr!2Jy zjga%Oa7kWDk`G~h$S1s6#eCzdf|C#ZCxYesMtHG2Zp;xel(Iyy9HbP1b< z^dCc@5c(>WGBqD*-wv4vzf;n$D@~I}ZXd!u-u$CP|CV6xGswQTkvm^vX>H_wFVW8w z%sQ22Pa{`fV!7SOoi5Q&7ZO%j${M*-C6<;(?qrF68nAdE|J`9H0yl1niBmKK~mhvRhKxgHF4Zf+}&n*K0J# z1sv@~RZU$^JgT67jaW|dt8ibrfhIyiv=<6rP7YMzNnX8O#g(-4`z?2oN*H@F*x)sZil9wRRZUq&!mIH@Tzr;nuf}os zdNFCK#z9`a+L?@2%H+3g(ZJxj^AH8@%RMHgw~QsRCTKkv1Il8)hMIW2S9Qu5+ah&A&l@mU9P z&QkK@QJkYo>`qLe2-}kyUwvk=PJwo>1VY`(3W(qe6uXqX_Y)@i0Lpa(8}(FpPgfR~ zFM)S~FMUk2B*44LTrnmY2wqFc$e;0XuitZB+1hog&m{r1c&OJ;-HAtX$!oO`#Be_O ztQMQ)-_XSN>VK6>uGQjMiVbJrhX)u=?04CXTX)6*+YFbGUQYQSXjf8&JSfr`v@b#V z^JrMjz2pkoOK$@K=aP4S!LQ-Rr^%^bAV#;GUR#I92mSO3@Il4ZcQ0FeXy~``ekh#g z)mVL51?y#HSCM&j;3bYv9GmKJCc=|GA?lO32TuNk3_poydlk{)L3_hc>B~+;-g%DF zllW_dhvbndr?3(C%X9Fja1N5q`mMTB;L?91+-W?P8QG9Jt)EryhPa3OkmOap!QocmGp4HwCW$Dd`P?OMaB| zw*VK7f5)0$GCK$gxzuiN2}M{RIpz}c$lTxY0^D?yT=^YG;LYDsC+yJ&_SD=zKH%rO#i#SBFk@`jphEL6XV;3$bRTpt2UbfWn>>~Du9|2iPdN$ze0lQ9C7Yf|2 zlkr~&uotMko{*ub8e~5F8xrS}zL%gMwd9iNm+)}>{$ld^CETme{$;aDYCdMgxb`;& z#k$4#FoP=$wU5K~vFOdk3#Y?>^pKX52P^78MBPo{=|uR=rVHbPaGg`%%h)bF@P}+}A6UvWNzrvsYwf_oH>>Lx!->g{)JvO6AmA7`13EF2 z47>?F$Lkw1{U(m?o%xA(Wqy^_@3PhZq_rou_Gq>CLVw-9{dkMxz)id!<6mM20@*nZpO#t&wH4|uYOFV_wfu-x_c0L=RPjPy+0zB7g#wBr$Ns?f}{&r!*K>q4ZG#&5hVa4dhikX;sN$owon56-b8zU zyYUe@@&KCbuaC&p2jIlNenfN+@$ylRm&{l7_@w8k`V4IpMD-msQ-P`nG3d3k0pI#R zLcXRL+uOkPR}WlFe^^7+19>hcPafj8@c6GB>5pL75|3L#-g|=knjd8Vv+RWNb{aQe zxFJ6B_B8bZh+KZ&I+x_zH2EL(Zc@xO1JGD~K)&`inwU*aKf$rM=u1bhr+7BPqrY@~ z@(e#lhPDqWvnUC6#aQnOFGfFV@$f!Lemlhv-X84=7kYG$vOolO4GFCuI?4nL7s1{s z`t+)(Pk_uP$Yh}F3s?xcRavF($;YtvazX|Y=aT1;s9OF8%?%C#Q>L^JNh=b?YLY2w zV=K!x7_#eh>hP#c_`MO!=udo<00APj7Y?JHMA$Tx7>vfh?`iH>$Sf-(eVM< zBo-}|uc1U55-QQ^4@iVWG&cBSN($lH2cHiql77j^vA*iy#qdK~!+#i;T#-eJB%;i| zFVV!4R{uvOXG-Ct41eu)2zap5r~p$O$RQ@F=uO3tjsgr^4;20Z*(Vjf;?>Jlg4LKz zE9Cb9d}tx+ji+RhXg5)v;`c@E8qo~(i%5V>^a}ROBJayY5m=o=cFIH??qMT!GEpf0 zVi9SRiGmfM{*%Wa6)Ym*?jo!514`3a)$P-$_ZE@O?xL}HXC}GfF1m~RFCu?>h!)_K zOftn&6eE9~_LTUCLY^%)Ce!h?rwGo>N*9u1Rwbc7_xMd6CfCfKcp z^+YjTKU?x6$&rh+BTqMnsM1m3Uo-c5z}4Xv!TC)yOdxeE8x(sJY$B;|wjfP3hMV6# z9$$fzUl#6}X8i>}SF}hb`MQ~0my3*2x}K^3kqlIbdXK=(oT7S$tV!gZ0Q%I1PNab?~i~>Jt z)G(l!8fB$mS=CHNdx=H_E^m&PG8Xw``28|iX@kU5O>lJ+UM+i@$md=ngDR(4+M7}8 z)snu~l$_e)d5tu9iTVxO5~!$4%}n`CNRbFLKE+kF!ue1glBllf6d8A%8=6=@b$`BE z#LVXy$Tl}4a}knwT_b~(qEK60_qyi^mW<|V4>;9BNyxqpYRg5rsw%np$Oyke=T0l? z{INqV=T}XdLR7`!&hsLMt~Wbu8rEIzdxG=5=6Ds@6!xvYqGJ2I#M+xCy5t7KJ{zYI zSYIu+Uwt&g+f|O`dumWH;-)6}q6hxK686vkx5)Ml5&P{cu(Q#5+o`aL3{;6Y+u}lt z*EJdZZquyJjdYNa4_?}#;VmKKFUAZ_sHtdq*_YGeNVKs?|6ZY_rU`x<6MifXJJ&X` zK5&_z6~nu|3-K+1JN@_KXpK+tuDS_S<8{qZ^UKKN3i4>%(b zO}?-l*(jiMlsxIOjMc&MGSI`}hmZ7s2eR!e$c5@1c zLL||0ox&-*O1626`q+wH>a^ZtqpL5&kNJTK@&R0<0KRM$(aj4m!l^5+IzALEFE;1& zbt&OvUqvkw-)Whz1$%OHPR|a@I9GsO`g?ojRrS}3_<8~tDsnBTHZ3?HS?kcEBc5?`lL_%)JJ0G0b9@ktg z>r^@uT)V$Fn@8L8Ex~DS2FHbuTS^ zcJX5SyyjQ&6>r)WV9O!R@e*pXhVTU~rUe%FtL=t+t%=Bbh=Ky&1`|8`ca~Z$NCs0& z06%q`(LF@!z*)2rf;u@If@M$#hedjoEbbu+w!J|sL2EM|SZQq})4}xMd3|Uus&|nf z>EE0qW!5I)D>pc(Q(gF7Ggup4jmE$}#}#|&rIn700FZ?UPEB*i_YbrSyPCGH^SY9| z>IQbc+8mN)?|Ib*Ev(Ql6%w+X&o#$C?=o5I)hilLC2^%R9p zmp8k9I}bMByuSfBYP#Ajb_p84qgqodu2AH&Yk;8nC` zB%`5;;Jk#P4MII8Opv%Y$M9dcXKCq>7=7sjk8-8=G)NckhybB2EBCfh7;7>?FAKk75C_UgvEe;?UE=LJQY z_4Gy{+|W#u)TCWHBlukxCnVC?*;}j7Z`@>0Zi45AO>kY3zQM&vu|2;@tAn3I{p`OG z$H9GcS~f2Yk#_9l?lw&rqhGnn9E#lBSr{G829jyLL_KWwuAf(ilHHNy!9PE@ypvu? zqN9ypm8d2yqrop#6p0d2x2fEGL%H38{{2m0f`q1oK<-;XzW@-+=q4ko+$tof;9hIb zCb(i51UFrCnrig)eBBkF+G__FPEJyZJ2Gquv)z1yxX%RrbShvJm9|dMPXokmrq=z` zWnD>j(?5qH3}b@dh)4v0)$>WK$7QSM(beu*$3%X?ZuQeMF8h5im3=foIpe%frQc_8 zqy-Ko`UCzm{Q(XP^AuQ2m@?Y46ALXWnzV24-db~?t0%%_Q6d+2_0qs=KrwuC2&n0&*Ry*8$^9z zKtvRTBp@UZjzm;c&?FK>1qD>V+aRLWV+E#39El`6; z(JHlG^{xU|tyZlk^8T{{di*|rKA%V4-uq@}XJ=+-XY0{#a(>0xjkw8%gIL!e+FyRw7Ep6aCrE@g8zAb;eGI|82H3AnoGS4zaf zV=q*H|R2}hI9TkG?jaiz)cSy7+pqTjR`lDi-iWMlQ`QF=j1 zBc?vPmK*LN!o->846aH!? zE3S#p@I2FQhsT6Z%RNUSDMf_H<2m<9mRKrRtTMo<^sLuK>(5F& ztP^4C5(RP}O}Q^U43&||JTqonC#9o3_&~XBTYbSUNtvOXqiUsXMT#0PI4zqkw#LuN zDqNNIUG$EK)P;1aAtF@VyP`2lf2^&1ZJmR&jM7`)tIINUM9@a*ZSUf@;K%bHjtg>J zd_M4{oyQ)=QAbL1Ti+Tf`Z2f5XpiaHtz9V9&yYyf#^&Lz!r{H^f)(kVBvQ^}Q&D4p zf*txK)yw!Uz1Uv9yB>wNef-sQN0KkC_pELM?fj^x7|g#&Bi>dM&0Ns?QLh~D&B)i> z)|qv*&Z8~InvR<-k+*M5r)C{%j&a{C?}jnVtdlp#xNepkFh*|HIW@<$-fWM+7$>u? zRdbAdvppPRS|ROjj*)G)g<%XjSZ`WAxH(=<6aRM;Km8Iuv%>t1+2Q_15or;pLDuK9 zTk9_*A2T_C@iRqWs3fwm1sELH3k430ZyU)QJoeHW(X|N(_D%J#giB38D3xrp>#Mox zk?DMLz4h5_XT4*)`&1~5Rnk^2w(@#sF>6n2XPxI2FPN>QUTN~|I?pX~1YtLn{dU(^ z&mlFEsz$n|Tw;m3rgh`l+hca$4ukb#>`En>@g}w&=Pb)A_jT44UTKb<%wwwr84v!b zBop6+Yf9>oBcI{G3zsOBZ93vbBEsFE5^PiIcCDHsX6+9!Ep9}aqi!C`94`8u#gRZcSeix1DPo$Sc5rC8pP=O`(*x!l%<7xu;8m80AQ;Mv~KDVDdrt@Y#I;OBV-MS0vAv|T`tv$j9*pMG2;?%JbY)%#vmpGxNPYpKKe zVJQ9RM$36G{xYgje%8xbmoBUBIz>^~1B*T8WsiF~eTa+_&+)coJLAY&AlZMxtaI8a zHL_jvs@2OBg;Akmj^z;2AIrf`PVZp>t<0%JY6g&(172T9)#~+%!d|%i-Nl+MhrFtm zVMauV8&>wvD(B16F%{aC3MfLmSQgda;{%P8$>b*?XHngV1N~q7Y-d-`)s3Dr8u9Cw zH{IKpOgBr$Bc*t5xYx?Ve@U_Z|v5zHI-R3bfE@-NQ*{bNV|?VIH1 zdH!viY$xlriwi!L_`rYOXlspFra%447U|$%BL9~1@FR6NE-hoiZYSfII8-sn_Ffh) zp=^%RW@w|lOFdL~#l?Fp4n!1Dm&$q?k{q-F!LMvu#c(|QkXi-sCQGQ@yDol43v?H5 zlAqxHn!gEcjVwRlr)0P&(Wb!jeR8d@QjN#hb2?RBM=no)PLgZu3$9Aou^3l8AivzJ zX(%v!5Q)CV`2X*%yw5+q^=-5(9KH3)u_rZkw1#<-fY8&XP8IYCAStc*=QFUddlYU!@sr@6cOnXj5;jWIY#O@cv= zOh2_ba`E4hGJR%KoNd*=;>I_{S@!%Z?s-E~g=znad)yp1|6g(Uo8oNC{}uN;kITX1 zS3Ca|d8;X-|5$`kCX{Ap_~P+euBUYer3veB+0!wAdfVdPz%u6p($zx4pxMbIAES z(f-7dC=dT9ku%e=d3f#?Po_0B+H(Dd{8?@B9FF*M7o@mnZ*U&(v1DmPPPagTvOlLi z{`S9Wi&HR@zpYJOQ~dGMO|Fy1P%XFG`+7Fa*3g(Z`%b(( z1G}xrMVyu`wc+`5hot_%^h#RpKleE~^p*HcHCCY+ z#qBA#90Tz}vY)QQ4H}MI?d7gmr=_Z;&hI7pspdN6AO7DuA+-Z_^J&97QQ1;pk7TKC z>BNV(xDwH?ugwXw*blX2L7w+$9Zub*k+8G+m}Z6LCdpn^*QDdM=iPFsD($ETiwLED zIWnw5{&h4#T<<(fk{_%qVD20v5U`fT&Hbut?$=+u-rX(rj+5+V&Ha+U+1#(+{@br+ zwCetEv?|0ogYh^nNSICt#dAzAr6$$BtN#5Bas@7-cn=4&53T!0Ytuxr{BYLsat@Mp zukLS>^?6+tk&)H2VRIPml(VXdK3%|`G}9-(0l>+S7ZQLSMu$j)(-fK5W@HX-LJc%z z{-mx-+cZ?feya{uxDILik|f_zSK!cTi~a+N?ZevQeS8L5zO20`WVs7YN||R3=WgmG z+eee?;yR&KyBHcO#<<9#)**Su;I$34xMt%ng=kw-d-_`mx!LB;j1e2`{p%4u^eG$U zz3bI8WT($c2z-(@tDIYEAVK&UPu4mDC|{!gr4A%z7HkZs{=$G+@O?OHpS*9S=A-_g z`Eym@N+g=+R~?YJ0VE;4c*vb**xsov zti%s)Z`*?EQZWn{h#MuOro;(9(N$hho741-t`-}9V-Rv0_%)WiT2n0_*Jj2~vB75G zgvWIQG9JlSC9PbnJ=deVXDFS0NtzQRL*5PAqO8P6ew`9!wekcdLP394vaeO*^!`Uy z#RUiJIW5Txo4IM(KkJYDb*1%~6z{}gD{6@T(RxcrefBl$VH7%BJ2k^cCi`2<-hxe* z!*zk~ia@nXpn-2D;FeGU&I6ee9el01WM6s7F+Jt`9LW98!rHVT+Ls44EqZ(Y!MG&! z6p98TxYI6JJ4N^_4HXJo%w_a2N4o@XxvW-s87goC74r+KPVN=6Tpl!OBumh00&PpM z0ICf&m!U#W+qeAy^Lt$%6K9#k=P_h=rp6 zV3T}H9rBNEI@U8X9ZwpqREd=Anukar(gapnp}_@Z2M@-$tW+U>^qj-rQ9BjyMk4w9 zN|pS>OQO5|&?SrglD+&AY%);q%o%lY&-i+Q5IQTN$XvxQxM^NGEZ_Z`!)TiKmhykc z{fFbQeN>0LXpY(SmSmsIi6{s5{!7rg8|{&^6hE=h0mIx%YZt-lgKSVJvHf_7W1(eu zZQvZdi$p(Bl3VL4Rb31vxq`~4x0^$0hRv98+1Xc%NQj;Ql50H;A{Xl{BWpe9INr<^ znYNX6YAae~cha#|U-A)uU$TvDk z67jBDUa5U>t!VVDMA;o17*^|hmirlnDMP z-ax2mP<7_@S2^l83MMPgEprJBiKJ~4?UyXhm(Vkooipq~l02o(>4#?U2S}FWx`OYU zLrTe#ROfV%hw!hN=Kgf^UrYI{+ps;78U*8QxEM)y3#)%GThX1O{}}5`*w}-H2_t60 z@gCGyDES?| z0rPs%8^W9!FuFH}4;MjYZ)$Lwjt!k!4ljDsPrRpbTQwI!oEYkgw^)k4vOh}O{(-ma z5H#dH)Q9#LoM!-yra400YFHXgUl)25l|7H9ONsEy>av`^G?}=I|KmpQGNr5H^)d2LM#5&oC?gH`P&-nJdgY~Catg+A(;ny6fwa{?k zryS@QhxJtEz@RvKyz{&KEMstVZa1RY8xf^H)vY{2osSm9%X1)X039pL&VhFZV7W;- zaA*MSB#g^}3j=77@Zt^#@f3vN)5O*c)dPf<@zUWX)65)gGD( zb%`|5=~+o*zs`4|_YgWl*s~alhS09U_Qh~u2pujIEe6-2G(;#^41I>ux$UR$&6I-c zlDfK4>7OqSBbke#awvBC?o_xllm>S&Oy$j>uCPf<8HjLdD1qQ4>Z{h__y*wPF+yS7 zGfZJTg}<{f9Gj*v){jJ_84a%`(Vp$Dansh?HJwpG>q<0>VNVkE6O@bLbP|pA`hh13 zDtEI=(Ml~;4d;hh+L6|1HJd8R0N@+e%ukENeBKenEV1aT~FwEN#nk@%##Ay2j(g ztz^v#I6nfX>7Oe=OrEWohqaDY@$ukf+hn!l@4+BaK>x?pbAa z3=^TI4AdiOlDy*zYuia>^F~rL5te7cx1(r;@bz-IHws5UzX?1>)A>T5yRd3B4Hj-? z!Z)Mo81;!vLH&+lw-g~$;8^lCSjc!s?10Diu4iG-h&>ac#?Y^YsO9j8{~nwIyT{V` zhKW2Cj|43dmx^*SfrqNjNvS{lg>mR^1>;6La`21Qc#gCzNFPT-4GI5=jpre!aw+xa z`{-(bI?DCuaevor%!0CUI166C3%~Q<&z3=#@wB(_!7>;*p7s;w--V6i(aJ0zjc&)& z*!B|cLH7Q^d(L~-5toc(&@t840vFrK5e#7=1sbj zeVO2yL6yQM_|X~EuTyCz#v@qtr!q7|J<--G!&zNYLf)ASvodIcu=H-(p$v+iw+l1C zcM?tCJ^??U4wIW3omU*<%Q-@$HM^g2u9Ue?W@Lj|A*kfh;=Tj#l z$n)XQ0vyxTW6Q2Bpa+PsDi1a;q833h7OpQsQs6umglxLTDH}^B9fOV8bd2CR2cBiq z8N%mdVDe(L+5B@hyt|m{+TY@fwX-T%7Wb1RE1L5(&nXj5E~f7aC1YXyTlAS=9a}as zhXxX1;fIiyOVgaD97FTNV{j#xHVQ?f;YuFP@uj2D4;fu06dxZaA;R9Qva+}7NW zwY7;PrNgyV^c`Fu;eYSqoP047_Pk4d{raY3*HPVp>lEK0?ZbnjShKa>u(gi#Oow~# z($1C$9_w9wuK3QsOq|puuj_wI!#Sg#Xy?1-N^IBRmK@vs+t`9UP2&}IE*g;r39G5b z{n$t>u}_yP-jJug5M8eCOM`;dG)1e!(#RUMCgce(K~AJ)nL9aVrsUlXfAL(QVS+@C zrU5BJcvhx?cMD;H96s!sXZ1aLeW|p?isttx`n6ZXT^%G@OMsDaZmSOqwBbQYlP-M%HfB7mSA8>u8*?e;GOKbdF3dD~~oE+yOZXmJ0oV z&d3q|Q$-_h7S-FS1)mhujai2GR*Xpby~@86jo{3p{r9&$P^r6xW6dwHvO z0=@1Afe$G^p7?Lxr+bARB2Pm$bAk!Nnb4>m#bkN2xGyBhrxd zsjzq>4eMN(iVY`UyB#ktk5vqm7o0}AC=;EM)g!>Zk&g9kGr}<_15w>6VrOmtlWaM- zeV=K!O8QSz!MF)6wzs6ho15r%xe<|S2dIkad-B7GpY!4CVwxA!X*kx95oF8F;@!-c zY~xGdFC5G$G|8-cCAE_wc~vS{H`5T;;r9`*cc8H#PPy3QuyHf(rJl`kFh!kfDAf(< zCZI{_NMe~y5Y+AM6)!}&>dr9uYcoQpG#!*5&;VgXD#U$2`?rn#1+O1aRZ5oFUtsMA zbfChA_ar}X!18STogI=2_dY;sGyFJ&eMr0bNBz<~InQ*I$sXgUAfjH-w{|-nCLL4N zgt}L>O@)~s(#WV+Bh>0#az`q!ELWd6*+vZ7lZMt-cp!YhaQrC4*81|$a&_fN(vJs4 zyi!{1fOZS!;c)Ros%{(V=+z`i9{LNkD#1aTejIv~P_>{O4x>s?$nVUHp_);BA_;F( z?!ZIp(Dqm@as5|?ZbUI0N=v9$N7XNai(Y052#i#yx=H$OlDYJuP5BF)DxvW{*YGW@4N85=p`r9+%WAJ zdWyTPzdmmSd|yh_1@RZ?v;_^&w-3YK;gYhA|6&*MxMzAI_V(I{@=pQEe}m1W_;32L!&})^mx>{!lWA`Uri1^_StQThbhzkfNhz zu?NTTz}#6`<@UNW;=DB_SMx>v-lv%`c^my-q>NXkKlRE$^=ZGgxBNz`Yc#}A`q<&~ z?qv!lwkVqTs>Oap@#zm}^AQd0SkDvD{?FiY-0Y%Hap_?+1=!D@fgvB!?w#Hkfr)cm zBJxWbbLS~UuiSacIf)V0oZ(RX5smOXb*AYa4kgy7!zUJ>q)Bk&BRaF~(KAlZB-PK2 zq$CAKZ%2Wo@(g^ronF@_^9FCA+3Zc`8Ft(LrR20#Qd*d*P_peiqnh_hKMyaQ-*4Z0 z1`d6Ua>DP!;K9d8x`I+5W(TqYsuUQzgZc;`oqJ zpE!Af5T};OCYw@wIOCdG%Y6|9y3bd29R@=`!I}QQWLW(PH7P2SF#**KYkead`g48P01tkaY*C!>1*OW(!Ok?Ld)&9&xlG@pJcFp zN;?PzXJG!PG}blmjK)pufcw8PnQZ!xaQsuMPhR{l9JJ(1RWEtsT>LBt3KL_4Ama#? z)!rlRnnty;LBFxVyzN`d!shY9y(HU$Gpe->`n4E;*gpRZB$2^p3Q@9sni_|Fk=U?*Mem5LcLOVf6Sz}4m|yF`4GVZtsN==UAR z9J5QW3>STtM|)Mj27SK<^GDvIJSDN0W#Sq5XcsO&u%aLIQdtgs}b!0Fx1--8qlD}-7iLZI6_AxpZ=yJlGvS`9SRuYBe#Gcxl|VR`SMBxV?w2Rs;=Q?5r^_Czf~Q>3P1Gwy`slt(;VbXs3u~1zFu4Qz; zY46V(ReJt>H)pvl&Qw(|Wt}aVcWtwN3EuuRJR(wA(#8NkdpOlY zVD;CizA8(Eimwr{u8DBvYZ~bBIsYV75tTg4b>9YSx5bivOiHC{L$Zd<_P@$E&a&1ECH)f#Wmt?3gVI?k%u}oHsPR{2%jB9 zx>uh7FAmbrT~dBV-0_hW{3MwoM#BE@aN4Z?v&{Dp{Z#0%CmMZ*7vgcPmAD||`x*Sb z2A9j}kM64N!F6V(D@iWDNG*>zaOJd1mA?R z8^@_Xi7=$MQkofPLrJVk>${{fseEKLy_6wX3XqHN_Li6O1tE z1WuDABfNG3CE_;*mld3#VWiVt1YpD9W_09xi>j9rnsFLy;KWH9B;1FL_cW7;UIku$-^s~VpC zM8o|(_$mwIjz#fK#mZ3s zn876yv?grj9vsv|T&PB6@|1Mg`y1`p$=Dy0UaAY8OX3Z_ja97{@nWUqrGw!5Z?vzl zcr2)H(($HQ2r+(9;C%dDk536c+wf^RMaZ=stxbp_Xz_64RG^P@pl+&A{VKJ*Eh2*b z`YF}R0Z?%h?Rl@B(ho65^}qW_y=6XGH~^bY9)w<)v=(!QX5c<`sWW+lM_Mgr{S9eK zoS3Q3@*`_37!~Lu1 zs;Ikp{m8o)cpFw;-Cn&}?5rKVCBt9Cn;6UEDs*OCK97#UCZ;RNLf(YxDB6RbfcPHeRF?FuD5@L+tp`p?EM* z^dRoMCxVMmtq@$O>N`{02t%TvRu4m$ou+S05MGCDS%+ANtD`!%k!H+`n`I@L4rV0X z3`^>$dRQWlR(&nC#1H1-e^yMNO6++P;#U-*_;Yj&ITVLE)YG-G9h=}N|_Euv8DdDlW3mf#M!BA47x^EO?(^E7l8C`v+lFCWG zwzYzxq+E5|Cg&#*xpp2dQOpK8xE{18Oq zctmRc3suTfd0QuK#U=MDlsRxGufp`m2zhs?uUk)^1y4#`*Y|&lYiYMw*mDPk-822m z+T5kz5bwDS4g-*5$*2YwqE84}N-wqAt#A$b&IniU(P&|4f9UcD?c}?|h!vp?!F4I# zM7B2vG~;o5q667#gyDan(nL`TEB-)QceWpV{|7A;68b~pecVnp_J_syX^G&~AN(Fr zPhoyP==lJ*=Z^M=_aD$>0?r}ppJ>4Gh8YU}q!!og{$wXd5rfLTv|T^A@F!g>{N5M- z_mEx}_V$I8M<~I5)c2U%(WDEi>S(kDRLj)j&eO(zS?)}9$HS{p;@u@&nUd&&+cr+} zuU>H_v8i9IW#wtDXixhY&s3%VtXhYc!abr9?tS`UTOu?>+71i) zK1Xb9O?VS=f~-c|NiLhA|6`gfoHc{}G4*S8v|RvlJppBR9#bRnxoH%&_7KE?5ikj>9JiJ>4F-`-INz zTs7$2A~)x|xDvF!Td!}zPV~sA+T0HoKE)OLt_e0i#f`+RgW%7n$Q8;n!1Wm_T?USU zm}k@~T(d&SGrCdu+6vLn>15$UEByMLc7e+0w4<=b5r`C)TEXoFZk$~*!^{^rBsZg> z;01P~-)=bg0$HO|10m)m%@EecLg`EDhqq8vyrjj#pA%qw1GZIehE)w%-J1i;K5n3T zTw|-@;w#)Bxz-2PHR5(hx4ux_NaqQ?egcbx1$NZHT#5E^i;dy17M<`^h&+^#+P+XO z(RYUb(3cN)g+h}jW=>O+?|Bf705y4Nf}csg<-wi$=EMU$6e>Cw9W8Yn4Z=f{6`W7p z_n%z5`>rcx%Jv={|3mt!tK-eC#GEjIl=fYBhN*@1eb+r>I-$M~1QIqvNa_QN2{Q?g zqRYw&drXA@bJ>15YZQd^Ua;SpO&2!zfq>SmM$p#4v(_v^co_x3ZJ4jKsTYy~)1Oh0 z)P|*aheq?B>cq^b3KGoU(Q3JxcP=OzzH7rec`KVDc^1-zzdMpKcjsvMvke;-^<~s~ z(+$_fH;m5p$^58agv*092_&jwFfY;A$5ExD^h^GZrDI$$;b|YpZp&^8Gom0vWTirE z6v$mze_?HJ805l+3tgh1g#V80Q})D#X^EdJFFj4Kv5J{H)ub&C#Sk7+S1L%WKG3%v zTO>eF__iIJsy@*hlMN?>nsXoHLD99TG|zAE4RHztsz)ijreLdt^}XSRf^`>G^ai~f z(+i7xL#7*x?tBzEhic?O(FEbx>0U)6XHT^*NN!z0I`)Kb+*n`-m!4|%D3MmX7hrSl zG8Njkx}Jo;+}Lv=xEDNd$Ev>T0sie-58?A3FuFY(*d`Dslp+^>)l`@5ZqIrV;fvmI z+k<^5%Q51aMft_=U?1i1ykZI@`Jw@fNkLU&9i36_e1s6Tp6hYn#Vmq<~ z;b9c4>BzPU$D*L87Yh?UJ^_=x*f;Ww?j*W91a?A9xEcd%JFzGsyBD17#Il5eQP86^ zTkZC9WKHPkVl;FMi7|JP5mgkN>x>}(CK5uu*;V1U9^mT3=8jz+DbnXf$rB?Vw#$uX zZKVef=01>CCrKr3+O^ITW`q!LK1Cd=oTbEzziaZ)BvBZ{EK{Wzfeeon4maNE*$H&E~fZ=4`>7 z^EXG4d{?qA?gn@^F4?_9B(})CghZ(Ks4F`Vw@9!l5&F)N@Tn4kz@pz*F%RK^2|QIS z6R%~4Y!#a;wC)BERqQq4yf2JXGqa#9g)M3vU1KR+RI^Q;b{GZ{jTsla3}1C+1o^8w zwi4w=wisZQKMQs}h3uGDbb#?L{yIlP6~-z0bi+KTR78IxDA@Mw_I?11cFpb)U|bd_ z^_$x(!00>_1_dy`(Oq~(%f)A&24*?`tifG$w>^G_k_hSGr~#dyY&HETrJE`@h82;JXlR~crH~>iDWxo zzU6BCh5S`Rn$?5zd8kF)@;QNO$)O5k)BdI7>Po`>{T@?Y50EOp(bt5z9Zj%&Q$78W z%D*S{3S!~zV|aPddH%utnQmEW9;T1=urP=P4&AJ`_m!n5rpR|>b?_QojY^q;JSXx{ zTk9RHYCI3xw>>L#w|x5SKQ{o#rsMF4nK4}T$L(qe`85*m2eCNeSS0k+pu^T_dYGnR zMM9h&8Z}JcYSY$w&(hF=&_m0T1%Ev(*RsK$Kj^W6Dkh8X0GVy0?2bkc>EU-R^EV3m zsJW^qhPsJN>95evRd_i^T z{s`zB!hC(sM_@J$dRRh3!v>Bx2&Hu1Yw~df%nxDejvqvvHtN;73B~Ttf-rqTwW4Oa zmBiyEq#?}PV@<>{x0=uiXec}*MjRZCwSHIt9I%_ zBF&7DQ*$tw;wno?2(C#8(VP@r3LhE-^dJ+`&Gr@~>sTkjo(yX_&EntIkfADSjJl3ZmUV+Ip)6efMFdeqz}ZlyX)lj3%g7q-`~e$WR4Ls; zBFLt0;1~IP8^*c{E4x8b7_JG?bKvbTY{n@9wuiBD!O{(;gtH*wK{qH0XYsZfmcvb5?L}HgKv@JE5&S3|BW_ePJeEWr@OL~eb&${b zKbit9ICm!;dg!s@uHlfYXIkHdi)SgNow0!ABHhA_)e z_Pv44B18`nk<6Eb!_Y|9SCJ7`_%TkRfKZveOd{jLU~?o(5(b6Aeas}hr-ydk*+lnq zVc5ic6Kb5NyQLm^t_lc)rQO*qp?D@d>5g1SU>F4SVAndm!SjWR=1^as-^?DaVh3Zl z3jBcCVbG-~3+b51(IR!r!)rs!&4=r21B8Mj=$|hX#`k0kgm**XVoxNUb3-96ip2_P z;bnzU>|-Ltg+lk ziCYBZO&!!mvu?t59eBquW$XtWtavqq)9kZ4yi}#tcr=w;y_&6_vLs``cs}iK4#uTm zXn;|+6jk?Fu?+J&zD20C5&>I1s)L*u=H2T!{{*}MNIVqc>1*)zOlk$fo~ zb92URo#F?r)^s6rBVf0Q1^X@vU!(I~^ICgSb{1>hJ2C`0Z*p5Yu<2_V$%ud_CN`wa z>QYorVO`aUFvQHfg!vIL#mxM@mWHThHvO~bf$mn-)nNNrx#~(VYBeXoRx=Wt&vbCn z%wl}y7Idr^BXXfO17(W0ovq?);%I*37@leC58eAC%G!)z?aw-U+xyDV(I*0;gS_!o z)p;&=`w-Bd= zj|Z|o!dM;L9EhJHX~26BVu?iumO-p|OL&a2m`)bEaysZyFQYEa3=F<^jjbK9RqnC3fuq$Ar${!J}5^ zWcLbwF$$k$R(CWoKy!m*stl*X)@~tL+XMTMk2Io>bCQ6N15vo=-51+~L>~2m1yy@5mRNFmN|6$J|ong(rlN5!<^4sR}h3yb48ms>Beg z6w1kw_x#klUiPbw&G$$xkOUSUab0(MzDAH0o*x?`+pfUjdL^8?TVe=P7Neg_T+7;W zuvVMZVahlrBfsciLIP8|9za0l;!}>#eG{xoz?IBJ3)>S|kGA8F#}SzdZ(AOJ9O@ES zveOyNr0WlT6ImC}qrB6X=HTf87atExW&;`o*iw(f>_lYa3UyGB$X1F8$JL>}h-H~% zXb5x}f(yr25fC#3r578_8^V&?1mH%17e2~&;jN)e2@i)bcOk$EPD9zuHW8Sh!AIvv zGzh1xux}^|YqP^4Jc*^atmPks4l+@vSEPegNvvNE(O?u#UMUEF(TfmnP>GocP$bs3 zf-$O@rC*P8M=wc^B(18o9_8~>yfTd{hG1teIZ2 zt~k(3w-Ox_tk>tU2>5dtLZ?OxZo`>2xt6CIDxZ74=Zqio8xM((2e@Zr;2IAErVPbf zqTB}su3NE8njP|Tt* zs9en|4}wU%B9(auTZDg zBz72|#zKWlCty_?(|Oi$3{Y2i+73$U3STkSP?1S)Xy8;D8}7f8j~3F}eWIduz9!MO zlWNECTQe+wNoOlL+V}^;fOIx6e05Vs&wRYFL0y@SDDfGuHi`_^B^)N7HX)hq8&bFi z3&{iF`*hZ^O=DNgg5id)a4nswI?ipX1h;=h;< zLTa6r9BeNAO;`ARB%3Cz&_LQK6ciU|VACk1cDb{mW)yN(pF~6KXk^<~N5hWMsEN>N zpn5cNE#4Y%8^iubERZ*b1qh!7!N+6R`abefQmu}fUHwS)MkDG^n9YLo6)nNgGh|pe zxg5Y-SBd1D<7H;Jr{M~E^)zG5{2*937FY5qLGblhLbi z*H2wNF{Z6q}eX7^t$bQAcsB|@`+9rzW z*E6b<)g`-vL*@4c(U2^m23(eo*TSab6`Y>7#nmfgUJ3Q?VkS<&fxLn9*QbRcV44)# zu{=iOXX+#Aqb2hYyno3s#O00}-O={tDKYKPfwddD15dHfP8lzkr@p}E-}i?_8925R z20&>B8_?d8OFe7;z=Zj{U+BE}O@DZq!R80di^A|_0p$XW)C|DD3~{V$j9|tH7h|`4 z(@(D~025LD@LN~-X(9{gbD;_Q@a`r?VmV<)n`2jgZ|4j#A|gQklaN~ZB9z34nA|ZC zlT&M+i!KGIf^tGrWQJbwPeAY##CF>{m^lTNR6|v8ehM2JB46gB)=eU>8nMm7 zEy#_zB2vB0ku?U_JcPd3rDnQYu#V&hK+06MU8vH+i>Yjndw~k`yu!O`olv!&=t6=5 z;NWWrJ9!D*cnulVnJVy}#)h|%FBG)NYF(yf9xRx~y0^29$Jt@>ZA=$uh#H$6zMF=` zZ9^p;G`tQXQCW6q6}*-}<19AFlPj&T z6kd_cIb*9F-4~nX-eu!vv++c*wSw>GV884NxH5-r6znfy;p-T-NU-5`wn;dqf*y03 z+Lc|@R=8~m(H7yQHfqaxBC4ZQ_HzW4*~S26 zR4IBD+0>NiZaIqvpHV9LSvdU$o8n)U=T7>4daCrs^)g$FG#cs9?;S ztc2`_VLMBpO zEE(Sw-dTim%MS3_BIYO9*Tcz0Y>?ulA6AIw2Pm1~8A;o1&}8F8C|LzVve^Kw<(llQ z8I^qKJ86z?m?sc4Ye0io^ouoA94q2cUbSu*0@ld_hqBrHj+RFVfVZ(ijoU7CRDuwT zM6uukBrazCd}s5PaM?FhE0JK&XbNcz)fx=F<_DiHW<5LEew3ZfAb9B(lTGp2K)%-Z za%-)MX(K-lFBUU3`_fBh1fRDMnZF2tK5sF7>1CoPES-CHy<**5ud?1I73d`eF zjP9#R7MJ2Myv0LPk{_g-QsTzOCr4d>7(1@;3r%ujJ9XuF@}>mFT-Kq-rR(`e6PLT$ z7H~IKrRVq7S3En-FSIhcJUD>dq(ezIP}NI+ELq>sRa5R}a zcterl4FAM~xm*!-0M6yIKvy$KFDhPlnM(u*Go{T6Qm4~bG4@R<`hjr}8 zmx9v;$#8OfqIlzk0+-Md9?zGtP=c1ar8068wk=^{_;o)oVIzGP^5nmV^i3X0beV6( zkE@QbUV%YNIk}92sY_X;(8(V@T*`(A$>+%~egDkF0f>js_e*146WhhOOu-98ZloTx z-GG$ zaHQ|W`&O%GX-$@WGF(1gFzrAiT)@JKl{}BSI-(_;eYb;ZVGajG3Xu$>?`zTBGetry zy`nB@2-cyu{^zf-n79;$NwK|Qy2%mu_!Yz!;FP}e3SKKfb;;>hP*cD(QB^#z;e^q_ z>5w0ID5ZLQGyJCH5vL~@lWKU1cX`P0Xd()-4^XH_>q5iZ?1&K22ru7e;B41PP8HID zA+T{7ZgW_A!}rTrV3!15n`*VBleNxo7OIRxrG9bvBqf2coEdT+@l_*=a95{J$&1kR z!#t^P#-w3Lm-W1Glp9Kx7zlIJR4>`v$xO4QP-X~7G6y8vFQPCOrH{{(Q#@$um^VsP z)855L)_A{P3GS^ei~K1GvK1A7 zN}j7*sjI)|>Nd3BLZ4eTZ8gZ%=$L$6gOew!2hi1Zxe^V`Y%RxkY+L}rNF;a!9bPBj zlxB!{X!@u!QwjDJ9T0YXmkCghhoHv zUXl(EjgvncFsN(uN#Wnh566ChRS&~funD@Kd9r5j^O@Rl>XU&tRBnm<`07a>I~Et< zsM7eob5x4kI zgLx%W=iF;dIefsN{GXs4s~o;0LYC_}frN9Hctgvx!l_ zemjUS*M)Eui32Pc*no>BYC0Vj+vo;7UM_C&jzxEk&N4Jj=apGbH)6Jnyv!vIhfpzC zU)WUW0uTS&E~TmG<0NOJ^Pa4vVDbaF6f#xJH;w4oN?z9@z@xL%G|7p`@b?`Fy&2<; zrA-C*G#ZrYTDPqCTvYod@-?rW?1X8B%&hPJH1Cl#ZynOpT$cxLucLT1>w}_6FT^&` z!Da6~NnI-2^Huqt;P>#N=X?aBUJF+WQJ^xzkat)(=>c!O!^Q}Qm1URSVQYvmUJ0|_ zWrGOb1M)8GN_z53S&9PNx1O38=-(daE|K}rCgf|r_RxpUK-*s4q0}3%G!(cITl9N%yId*4xm++zYhUid`d6NQfvALU8NDq?2XRm3zo`+3=i6`p7J zkr-Fb3uF>!9)&y**ZRo$J1Q%1v2>&nM;hK0k7v_YU7`nqf+Hlqv~=)<@-?O zhrkw8-ofaiK{gzFUS0}#duNz%`UO<2VWS3~dZy29G*>nnyDz~{$E#`ZR`kge<>-i` zph4<5(K$J}Q9rM->WTC=z7K8GzuAcUfb;OZ@GpJ&GrX0$)x=}T0~+-+VCs9!?rhs2 z72sCqKIpNQbt8-6wY4mkOoz|cvJQg&FKB#|MRp$b?Ctm3PTTUyT)g0Y&9R0JOSw6q zY#U#c73)}M;hDs_%~80pd_RwME!(w@ttXHGEO4-;@DW+sP@5PMDvLLp1AN=Y7-Da$ z)tMypDSox;tp>Gv5((z-WKn}i4HG6ACS=M&OSD$CnkzK?c@n25>ZkA>p!44O_YE@w z#icQVFc#y{4IWwc9J3tFJ745H+hGuq6)o5Q?|#8wQlO8JHRfmijQa)Xxe2|JsK#<1 zVrn%*B|dtldj6yZX$&Rhm{94^?xVfpu!clYW43(tRF&Ky`lpnX=O(x%#VTzJpC5ID zwDq{PY^M@>pu&v<#Cvx+yt|&o!i}Tq6uw zaEOd7Zw}xdG$$biJScV)^4dZ21{S2Yt+k_}((&p7xok@b*)wQ~=NZ{x<;sX3jq>Z5 zVtIZPHf~^@J(qnNU`*N>U_AOsfN>kXd+iD^=6(Rjv5q#D-y6AGuWt4~;pGOF=63%X zwoxT;s~kK;LUuR8#EmS1+WtBU?{8#TK5z5Y95*d1R)%RyPsO^C3SIz}oK&6&UYl6= zsJ)JecBt1}N_O*i&24koGF`H%sL9KlBDwjNs{304-k2cW#4{)>K4J{FL?YR>(?fVFOx`t z$zKpt!pfYcCrSMx--QK^Z;@|QM57zTw3mRg+lqQONgGcKJ;`(Hu#8$&|UT!I9JI#X^96^2}5D$i= zkhAb&E9)9l&13lxSx)fSqs_tgHgqJLPwXwJHaswrLMoc8ptj>Y_#KSd#{Bzy*%E8P zb0aBaPjj%nt%?UfdtkB{o_B<2`ob=<9cGsYti_)38h>gn z?K@$fh)^2b-bz@p$oP`CoCUJcAg7-`unE>{~eSv$O8ys|NCsUx8Zt!9YI$EAVcX z4&#A;O*`B0tif&_+;0CK|$b zZltM_dV}BJ2tKgG8#q+@cpsm=iN+hX;N5)HCi=Efe*t$UH`Bq&{5E`!13b);F*YOl zyYRvMlZ?%_(TLR~uZ_RHnW`yM{v+Ab50YUsO*#asfx!Zk$?CK!Ay=b5SA~od+W2pq zX^v6-Vh?}(J8Cs*ZF~5l??9nwy2bN~X&Arp9S!nHs)$W*tKgp&)9}Y?z2Jxmt&c?s zT4`mL$(jM-B@mygyixx4qI+T+XvrYEML@x)z#1>XR!Y?a>V-iYUBzc?p$RGaV^sw+ zZT|L1s-CUPNn~N521Zh_K&}f6%NYsEwKYh_63;%UgrN>un_J1Nw?HcF$W?x63mro@ zR>r3D)0H%=+ty04%78SUR>hzBp7sjRhE}D?7Jse9<8#ZiW;cK5dm05S;*0NTdf+o1 zEtUW6-LIay#W(Jv4!=bxY$Nu;U%uc&w$eV2sr{>YHPyiva!s8b@KbD*@~ zsu8q<%mg80H3XS4*g;j?XB+M3ubRY&nJ{8(LnR-wjmG+^PgGi=sa|tb@)x&JbHJ4= zC=5)6f>Z{uV!y-x&_bVz1-(V+P9l}1>FHYFS}aFAN>)sH_dJQoge9de0EMm4DztE z;*Fb$nFz7S-k}S@(EUNprUAoI<7MUJhGqwsP(M`(Re6TOxvu!+vu<>~{yd6;)irf? zr3|8cO?KBva1WUQ!amdzmlIUp<(`qFQboh3hrA7yIR4?4%*wU53RNkEv?%31klBTscA9`_JHv#;3`Nc zI3{HxPx(XBTJ`&Q_6~}xA494;0dxIj{^<@H8==Nl<6D|NS+ZuYc7e0zicKScHZ882 zH}0U(Mm42+`Y$*dvUAkcGd8N6C)d8s+1DqQfH8?a)+J5Ug*)_DSNz z=fDKPB}}P)m-+gi=!hh?0;2%L>BGwUONBcuQ3b(l3vN6c!XQksUdTHV*_+GIRpjb= znMaq>38;KtDa{UN2dkz_zNKXu(pr^Pu^`5j(V+aPhk&6T zelWh`dd)G|r*D*+q36y-7GFopAl(I{a{eU0!_&Daf@CVsI3UgLiv|%1@ zddSHaJ=*-rhjUMz|6p>wTKR{&C;X*Hj6VE_GWwEljlkjY@B!sCTK227MCHuIda3@a zf=?|6`IuMm#fZrVAq?ZzgP&ak?PRk} zGi(<`l+CjQ5d~pp2=|%f6pJ!A)Y=Qp1KHo?GP^RvutiYA(w{vC4tf{p?w)JtpO#1% z_y7cV4OVvDQ-Rx;d{5&8+C&tFw`0-1%)i}52b&H1aUIss*I?-wjpke!6dWA$PjN?W@(t<#rP(x0Lr=q(-`P)6Q{;zbK6+y7qhF4mGaH3K(E0bs6pA>XVmcwAT z@WhO$CnH@p8^bchDl05Ou09=Gz&Wu6=*<BJA*UR~jj9b$>>1#@BajGJ@J1*T#HKVgmE?Lk1%eC+|Nf; z&|dNSha_hSlLy=VeF5BunEWS9o|gcC>|Fq$R^Sn&$xvsOuePh4FRP$EdhQg6PseiK z8eH%l7W}24G0BcGIxnlBxxS2h!1NrjpT||w*uWprf0o`|7kcN7HnM_0TL~)jV-7S{eZw#sIRNFWW<7@_!SkigLiC zFDqB37h%@0?6JODS21hm0$#Rt&KRFA0$+epAa+yKde_Zvh&Rq)u?YF&Zac5R3sn#I zTJ1{3!@V~8HvqXdufn_6GV?-=&HrPw)h{6dHd}V3f zY?)n9N5+bvUuQ?uynAKDJ&)OD)SSlaS=3@vo0+x(7K4a-fe+jZmWs-A_tK=O1d+kA zfy9e9){njr3tOUf$9Rx_7x*`O=_9dhH=22*jx0FPB{a(t=#+lyabnHO$)+yT#Cbjfao77x#}=UOi>;`{I@6(Gk9q16-%#Ua z#+($d1|C>T`vQDZ;(w0z{EB_s1e`Z%8Idf!Hzl#w2<@U#PTfWLNzf(-U7XrSejRQ}olni-%% znn_3>S)EE8$-c-B9-yIv*#sI%E7v?)R~uMf(`F-)#;ky6Ow-EpBc`k4VImGJD!5a~ zaM3Cou`B&W{49Ts_c}<&P1Yx&%uu^xb1Dg>Uq>2|z^)|B^0)5_wdW>kIW#iUTSI7h z%_WpL{9z6H(Y?<}#Z%r2Ycm1~W{<3caNip%iDXIXgFIT5hbA z+sB+6ZO>I~1jJX;Qxs-blm-O_m5YMxN;Har@23mA_aUnA%tN%FC0$G(d(9+g(NuF; zzPbEKk}5(9pApqT z;!veyeDv^AbKFxSJP)`>%=SE!5jg*9u@t)QCdub zczQkU9R`_TfULcst0{yN-JMok1J}Aw({Y}Xm+sroJaP( zj60n0yzbx!B&j?pzCTgAao_O00Dk-Pn{$&yDFp5xCR2Tk;qbNrR#bgjf5=e-)R znk22}gBs|-#H;t^H}HisMLu6*^A~8Y_W+%~+AG-^37X4kT=mVUl`u61@=qE-HCf(L zT;Bj80qI%`cb|ZiQlA$7b|Za}tmW4mX=0Cpvnb6nSq6JKmFy7czGX65dX_s*(s3l8 zzkQOX^!Y>toA<|pV30|;@Yn(b0@X79Zf@r##%tqv(@7u#b6QrO0+;xw^E~<#`eNAG z;wMglpCpZ2%_~k*rKk3@8$zYglCxW3qPbUiys=>O(eL^L?^(-96RrUbIbS@mNeE93 zSj|T@XPY-04#@TQ&X2K-| zga3NToh6{*y>qj@3Nw9ORfT zo-Lkpj*cY~Kg&zc)80WJc)Mu4Jz+^a9i2knJhl1drB*Gi+YX+>P1!}H%3hn&&L zjgmD0QiZbKhTYJc>WX1yIej-d6-MODxzAZaGhtUd_aH_ z20`ARg^?3;F@r&G13GcZP_w$DFtyciq>e7QU*SbQoG?F1Mv9hPF!<#x0U|5%s{H%~ zI(VQqk$@9l07g?su+|snnO{4L4k}8f63!o7q>*-Z1kH31 zZ8X|F`CPD6A?}DkEcGC<@0z368xZ946M|A{XV6jJcoDm}%EK>#-|o}Q)5QCwU--03 z^siU~YA?}&`RX>}v$})jDNZb{$)J5M@!8u9DOoJ7HBIP6pdF-IIO=NY`BmpFg``6G z95n?KEG3o|Y%KAeS$M#LnOkt3{3N1$XO3?4vst8^W;Y7i?kyy~o3_)4KCFw!>LEfv ziw1{m@nzc2`jxjl7|P3%Z6@|LaVe9Mp)U^ySZQp!`h*0gwe$?4G=A_h?H{RqL24!N zMP(T$pYkGM7M49q#L@cwCLVqTvK%UZ>Iw}H&~K6j zM`Z{$M^}C*0)4JxE;HW$DjgZO1v^^N0cgv^Gat`5JgImrcmnYl@SH}P!~6NCSLr)G zbFfS-Tg?;NAbXg1hCkg#3#FytnNPn#M@faveDe+J3VB;($X23Pi404S;YKU>zlj8MoB5MB z=?W>UnO_$EAChIk% zbLIxxD0|&w&JBW^db83~6t@K4V6Qhqco)MPf~Gigqb%28n;_ksq(gCJZg&V%nxS_; zHw>xt*KkSKoEvUdx|?%*h{_j&lc?C0@VQElX-eP<LsF#xku|&^{`}C0?8HS(eD)TtCVB7@cBkh21gr;t9UMRwRTUWz-V zAFcr;tl^)w(}~i@jr>kKxL@x!a*Lb38K|z2EQGu$GFyVk^hW-Zn`Q<*;VtY_hwSVX ziqdwS;-Ma_@8`{Yq=zPluw!o75K+_Be{|zgAZ8|FZ{+WJuv{yrKT2ou(m&UHG@Hfw ze2jXF)_n9SOOe`7eRPNomad%QCc=7=qufTAOWJmVzd~4y-!~^vJq`jJPVhC*6C|-S zd_Q4kML%uujh`M!m1`br{6n%A7`dI-6?7gfv3{6SLnJmOP(5OBq&lHeBkeR;nkP^4 zFC}L2(d)!~=0_#=1QObetbZ4^8bOf8n_^_?F=~b2HRC|if)7!3!ynB0p<8D2awD?_ zsAXuPY&?B6X!KYz<`;g?$i{_h+y5g&x_?{S)WGzqJ@_=rl6~~8SSVEfFDkxi3*Svy zs>C*OiLqp<{R|(-*vnF{lf~;9`#UZcHFBj3OB8n`v%9dqXzZ(9SV~aAI`mDgR9Acd z$b0uKd(X8lY&>4Wec3R{dWOH@i;|E7x(jH<4AYSWw7Kim!Uj2^z_&uODf`CXyygo*dCOf zBeR$;sskU-9DI??#sfJlJ|wdYg2?VBG(+QqOsuz$))Q$|{kA9#Cl50ns}>; zW%!RihL5-`i4*3?WBkzoHbP>)JU;*?2p*pW;oS`ZXy9!RKN!IF<+D@|_UUjG2C2U& zPq$&XN|Wc2*^4Aia$#3={e`XbM0jBCdydB%Bvw!Lwnv<#o(aHF88|gtDj$QDB-$KkQj4EU*id8FbVb1o|ddWwhi%0a;%CcrR@Tu*G`?vHtnH>d|6rtsqor z!5-gQt3mViIBH>}#;EVbqJT=TdfKJW6B6Vxwg8QKvLq3U4f>GB9y3h)+M9-5_PA=R zGp!T}CXF9mGqJGFyW0EWW>!^DYvbLFdZi_~qh`aUnL@DZfUt)=l2-*We?P4rZInX< z44n#Mi!h>7gPF4jD-?yB)CM%5J`Xfelxfnp@*jd(FPnbd?bv5CRi`+N>P`3P8rR8) z#>Z^URm8H7OcWo5PcmuO-JoACRyhq}wkg_4_ub{S*oTk-o0}jJyo~J{@i*L7NZbHP zx$egI0i9vzP&LS*{@OLSRdEQ;#zmkLIC;N<9BL!XUn1KDxA;oE)h&c-G`=i^4FHhn zAuMK!e#vcx#y8do>B^4L(QlwqR~gD)in8VI*<;e-)f>z%p47;JxS`4@9^vjdTU|;y8aSltnRLL>BNFq3n4@tCb*W8B4Nc?8Ts5l0P3u zACyjx&N7+H=D@@czZ%LSq|DhgA&m;V8H^Hen2PzQUQc*d>e)jiqlnE%s&vac(FaS&PfHG};59K4PU z-)onpBtvP}AYfUe_|p-r$~09Zyn8K9Fhied;K`BfW$Q1{qjKMUwxZoKQ(N9{ zS%8kibV$X0-JW7zjFDsYM|hKk^&hG)Y6k(pTx1~)0-1u1xJJnpWHs$sF>(oJ+pYGN zJWMl?NCEeuZXqcTX2Z>PYn1*rf6U7IOjh3(MMtXdwp$88yz1e$#D{G*vbRKNy#98( zWwQDvn!)h5KwBz8Cu`ownH^~sXox9+bNtWL%kf>kcnSX5)gF zVJ%65eaB1``%k#vfcoZSwj}nF=pRSkB%_n{ipX@Ty&OiT65^Z?SU21Z%YX82QgDd> z(+=Dx|4{KBJF}A>+JEm*=6lp_J3h|C`{S^7e@kg3vZxA~TV?5(lt#2reDTm9z_R{-Q$aVt9cyn9h5 zNp~gdPwY^d+}esAj&GGyZu_oi{qY@2qgz`pk~Sb|Y;t2~QZ`|Sa@5V1?cnbWVipLZ zem98Sl%^i#Up~ql`D|y&gCz&c3;I*=DoY-QjRRfhGwtzTQ-L)b4~_j{IEa5s6~vn;FNKIwI@vMhwV!Ruc5hXrD4 z9d|oec0TL7Ly2*-=XQus`ge)49;#(@X#F#mMY`juWdpe)7F+N{Hb7jXJeph(Udv1n zQ{Euwz3u|90R1msH{_qN!8Cc@n8?neMdYOLl*!mt$=|%6C@1gl5FMNWFW*0yDSq<- zjE`sbNq=!Pzc-l0kJbZqt6byM8$A_64dpfTXyF-if?v*cbn{depj*GGak3MhiU9_D zLYJHy2u;`gb?a-$aojT^(cnzznnMZXSXEG~@`kX`eBDpC&PMc6k58;&T7qxRZDb16 zy6V>VYn<8<4{iu5lkny0UJq!K+KugH*&Ym|cj)|NNgY~(U_GNGxyo~Jce^WSq`;&6 zci?Z7=s5kI5@nZ%eN-~ro!pF diff --git a/API.html b/API.html new file mode 100644 index 00000000..d767fc1c --- /dev/null +++ b/API.html @@ -0,0 +1,2241 @@ +API

nodeMcu API Instruction

+

version 0.9.2 build 2014-11-18

+

+

change log:

+

2014-11-18

+bug fixed: as a tcp server, the connection can’t closed with :close().

+tcp server: inactive connection will closed by server in 30s (previously 180s).

+add a test api node.input() to put lua chunk into lua interpretor, multi-line supported.

+add a test api node.ouput(function) to direct serial output to a callback function.

+file.readline() now returns line include EOL(‘\n’), and returns nil when EOF.

+

2014-11-12

+full version firmware

+

2014-11-11

+add file.seek() api to file module

+now max 6 pwm channel is supported

+

2014-11-10

+change log module to file module

+now file operation support multiple read/write

+for now file module only allowed one file opened

+

2014-11-5

+delete log operation api from node module

+add log module

+modify wifi module api

+modify node.key long_press and short_press default function

+key is triged only when key is released

+

Summary

+
    +
  • Easy to access wireless router
  • +
  • Based on Lua 5.1.4, Developers are supposed to have experience with Lua Program language.
  • +
  • Event-Drive programming modal.
  • +
  • Build-in file, timer, pwm, i2c, net, gpio, wifi module.
  • +
  • Serial Port BaudRate:9600
  • +
  • Re-mapped GPIO pin, use the index to program gpio, i2c, pwm.
  • +
  • GPIO Map Table:
  • +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + +
IO indexESP8266 pinIO indexESP8266 pin
0GPIO128GPIO0
1GPIO139GPIO2
2GPIO1410GPIO4
3GPIO1511GPIO5
4GPIO3
5GPIO1
6GPIO9
7GPIO10
+ +

Burn/Flash Firmware

+

Address

+

nodemcu_512k.bin: 0x00000

+

node module

+

+

node.restart()

+

Description

+

restart the chip.

+

Syntax

+

node.restart()

+

Parameters

+

nil

+

Returns

+

nil

+

Example

+
    node.restart();
+
+ +

See also

+

-

+

+

node.dsleep()

+

Description

+

Enter deep sleep mode, wake up when timed out

+

Syntax

+

node.dsleep(us)

+-Note: This function can only be used in the condition that esp8266 PIN32(RST) and PIN8(XPD_DCDC) are connected together.

+

Parameters

+

us: sleep time in micro second

+

Returns

+

nil

+

Example

+
    node.dsleep(us);
+
+ +

See also

+

-

+

+

node.chipid()

+

Description

+

return chip ID

+

Syntax

+

node.chipid()

+

Parameters

+

nil

+

Returns

+

number:chip ID

+

Example

+
    id = node.chipid();
+
+ +

See also

+

-

+

+

node.heap()

+

Description

+

return the remain HEAP size in bytes

+

Syntax

+

node.heap()

+

Parameters

+

nil

+

Returns

+

number: system heap size left in bytes

+

Example

+
    heap_size = node.heap();
+
+ +

See also

+

-

+

+

node.key()

+

Description

+

define button function, button is connected to GPIO16.

+

Syntax

+

node.key(type, function())

+

Parameters

+

type: type is either string “long” or “short”. long: press the key for 3 seconds, short: press shortly(less than 3 seconds)

+function(): user defined function which is called when key is pressed. If nil, cancling the user defined function.

+Default function: long: change LED blinking rate, short: reset chip

+

Returns

+

nil

+

Example

+
    node.key("long", function(){print('hello world')})
+
+ +

See also

+

-

+

+

node.led()

+

Description

+

setup the on/off time for led, which connected to GPIO16, multiplexing with node.key()

+

Syntax

+

node.led(low, high)

+

Parameters

+

Low: LED off time, LED keeps on when low=0. Unit: milliseconds, time resolution: 80~100ms

+High: LED off time. Unit: milliseconds, time resolution: 80~100ms

+

Returns

+

nil

+

Example

+
    -- turn led on forever.
+    node.led(0);
+
+ +

See also

+

-

+

+

node.input()

+

Description

+

accept a string and put the string into Lua interpretor.

+same as pcall(loadstring(str)) but support multi seperated line.

+

Syntax

+

node.input(str)

+

Parameters

+

str: Lua chunk

+

Returns

+

nil

+

Example

+
    -- never use node.input() in console. no effect.
+    sk:on("receive", function(conn, payload) node.input(payload) end)
+
+ +

See also

+

-

+

+

node.output()

+

Description

+

direct output from lua interpretor to a call back function.

+

Syntax

+

node.output(function(str), serial_debug)

+

Parameters

+

function(str): a function accept every output as str, and can send the output to a socket.

+serial_debug: 1 output also show in serial. 0: no serial output.

+

Returns

+

nil

+

Example

+
    function tonet(str)
+      sk:send(str)
+      -- print(str) WRONG!!! never ever print something in this function
+      -- because this will cause a recursive function call!!!
+    end
+    node.ouput(tonet, 1)  -- serial also get the lua output.
+
+ +

See also

+

-

+

file module

+

+

file.remove()

+

Description

+

remove file from file system.

+

Syntax

+

file.remove(filename)

+

Parameters

+

filename: file to remove

+

Returns

+

nil

+

Example

+
    -- remove "foo.lua" from file system.
+    file.remove("foo.lua")
+
+ +

See also

+

- file.open()

+- file.close()

+

+

file.open()

+

Description

+

open file.

+

Syntax

+

file.open(filename, mode)

+

Parameters

+

filename: file to be opened, directories are not supported

+mode:

+ “r”: read mode (the default)

+ “w”: write mode

+ “a”: append mode

+ “r+”: update mode, all previous data is preserved

+ “w+”: update mode, all previous data is erased

+ “a+”: append update mode, previous data is preserved, writing is only allowed at the end of file

+

Returns

+

nil

+

Example

+
    -- open 'init.lua', print the first line.
+    file.open("init.lua", "r")
+    print(file.readline())
+    file.close()
+
+ +

See also

+

- file.close()

+- file.readline()

+

+

file.close()

+

Description

+

close the file.

+

Syntax

+

file.close()

+

Parameters

+

nil

+

Returns

+

nil

+

Example

+
    -- open 'init.lua', print the first line.
+    file.open("init.lua", "r")
+    print(file.readline())
+    file.close()
+
+ +

See also

+

- file.open()

+- file.readline()

+

+

file.readline()

+

Description

+

read one line of file which is opened before.

+

Syntax

+

file.readline()

+

Parameters

+

nil

+

Returns

+

file content in string, line by line, include EOL(‘\n’)

+return nil when EOF.

+

Example

+
    -- print the first line of 'init.lua'
+    file.open("init.lua", "r")
+    print(file.readline())
+    file.close()
+
+ +

See also

+

- file.open()

+- file.close()

+

+

file.writeline()

+

Description

+

write string to file and add a ‘\n’ at the end.

+

Syntax

+

file.writeline(string)

+

Parameters

+

string: content to be write to file

+

Returns

+

true: write ok.
+nil: there is error

+

Example

+
    -- open 'init.lua' in 'a+' mode
+    file.open("init.lua", "a+")
+    -- write 'foo bar' to the end of the file
+    file.writeline('foo bar')
+    file.close()
+
+ +

See also

+

- file.open()

+- file.write()

+

+

file.write()

+

Description

+

write string to file.

+

Syntax

+

file.write(string)

+

Parameters

+

string: content to be write to file.

+

Returns

+

true: write ok.
+nil: there is error

+

Example

+
    -- open 'init.lua' in 'a+' mode
+    file.open("init.lua", "a+")
+    -- write 'foo bar' to the end of the file
+    file.write('foo bar')
+    file.close()
+
+ +

See also

+

- file.open()

+- file.writeline()

+

+

file.flush()

+

Description

+

flush to file.

+

Syntax

+

file.flush()

+

Parameters

+

nil

+

Returns

+

nil

+

Example

+
    -- open 'init.lua' in 'a+' mode
+    file.open("init.lua", "a+")
+    -- write 'foo bar' to the end of the file
+    file.write('foo bar')
+    file.flush()
+    file.close()
+
+ +

See also

+

- file.open()

+- file.writeline()

+

+

file.seek()

+

Description

+

Sets and gets the file position, measured from the beginning of the file, to the position given by offset plus a base specified by the string whence.

+

Syntax

+

file.seek(whence, offset)

+

Parameters

+

whence:

+“set”: base is position 0 (beginning of the file);

+“cur”: base is current position;(default value)

+“end”: base is end of file;

+offset: default 0

+

Returns

+

success: returns the final file position

+fail: returns nil

+

Example

+
    -- open 'init.lua' in 'a+' mode
+    file.open("init.lua", "a+")
+    -- write 'foo bar' to the end of the file
+    file.write('foo bar')
+    file.flush()
+    file.seek("set")
+    print(file.readline())
+    file.close()
+
+ +

See also

+

- file.open()

+- file.writeline()

+

+

file.list()

+

Description

+

list all files.

+

Syntax

+

file.list()

+

Parameters

+

nil

+

Returns

+

a lua table which contains the {file name: file size} pairs

+

Example

+
    l = file.list();
+    for k,v in l do
+      print("name:"..k..", size:"..v)
+    end
+
+ +

See also

+

- file.remove()

+

wifi module

+

CONSTANT

+

wifi.STATION, wifi.SOFTAP, wifi.STATIONAP

+

+

wifi.setmode(mode)

+

Description

+

setup wifi operation mode.

+

Syntax

+

wifi.setmode(mode)

+

Parameters

+

mode: value should be: wifi.STATION, wifi.SOFTAP or wifi.STATIONAP

+

Returns

+

current mode after setup

+

Example

+
    wifi.setmode(wifi.STATION)
+
+ +

See also

+

- wifi.getmode()

+

+

wifi.getmode(mode)

+

Description

+

get wifi operation mode.

+

Syntax

+

wifi.getmode()

+

Parameters

+

nil

+

Returns

+

wifi operation mode

+

Example

+
    print(wifi.getmode())
+
+ +

See also

+

- wifi.setmode()

+

+

wifi.startsmart()

+

Description

+

starts to auto configuration, if success set up ssid and pwd automatically .

+

Syntax

+

wifi.startsmart(channel, function succeed_callback())

+

Parameters

+

channel: 1~13, startup channel for searching, if nil, default to 6. 20 seconds for each channel.

+succeed_callback: callback function called after configuration, which is called when got password and connected to AP.

+

Returns

+

nil

+

Example

+
    wifi.startsmart(6, cb())
+
+ +

See also

+

- wifi.stopsmart()

+

+

wifi.stopsmart()

+

Description

+

stop the configuring process.

+

Syntax

+

wifi.stopsmart()

+

Parameters

+

nil

+

Returns

+

nil

+

Example

+
    wifi.stopsmart()
+
+ +

See also

+

- wifi.startsmart()

+

wifi.sta module

+

+

wifi.sta.config()

+

Description

+

set ssid and password in station mode.

+

Syntax

+

wifi.sta.config(ssid, password)

+

Parameters

+

ssid: string which is less than 32 bytes.

+password: string which is less than 64 bytes.

+

Returns

+

nil

+

Example

+
    wifi.sta.config("myssid","mypassword")
+
+ +

See also

+

- wifi.sta.connect()

+- wifi.sta.disconnect()

+

+

wifi.sta.connect()

+

Description

+

connect to AP in station mode.

+

Syntax

+

wifi.sta.connect()

+

Parameters

+

nil

+

Returns

+

nil

+

Example

+
    wifi.sta.connect()
+
+ +

See also

+

- wifi.sta.disconnect()

+- wifi.sta.config()

+

+

wifi.sta.disconnect()

+

Description

+

disconnect from AP in station mode.

+

Syntax

+

wifi.sta.disconnect()

+

Parameters

+

nil

+

Returns

+

nil

+

Example

+
    wifi.sta.disconnect()
+
+ +

See also

+

- wifi.sta.config()

+- wifi.sta.connect()

+

+

wifi.sta.autoconnect()

+

Description

+

auto connect to AP in station mode.

+

Syntax

+

wifi.sta.autoconnect(auto)

+

Parameters

+

auto: 0 to disable auto connecting. 1 to enable auto connecting

+

Returns

+

nil

+

Example

+
    wifi.sta.autoconnect()
+
+ +

See also

+

- wifi.sta.config()

+- wifi.sta.connect()

+- wifi.sta.disconnect()

+

+

wifi.sta.getip()

+

Description

+

get ip address in station mode.

+

Syntax

+

wifi.sta.getip()

+

Parameters

+

nil

+

Returns

+

ip address in string, for example:”192.168.0.111”

+

Example

+
    -- print current ip
+    print(wifi.sta.getip())
+
+ +

See also

+

- wifi.sta.getmac()

+

+

wifi.sta.getmac()

+

Description

+

get mac address in station mode.

+

Syntax

+

wifi.sta.getmac()

+

Parameters

+

nil

+

Returns

+

mac address in string, for example:”18-33-44-FE-55-BB”

+

Example

+
    -- print current mac address
+    print(wifi.sta.getmac())
+
+ +

See also

+

- wifi.sta.getip()

+

wifi.ap module

+

+

wifi.ap.config()

+

Description

+

set ssid and password in ap mode.

+

Syntax

+

wifi.ap.config(cfg)

+

Parameters

+

cfg: lua table to setup ap.

+

Example:

+
     cfg={}
+     cfg.ssid="myssid"
+     cfg.pwd="mypwd"
+     wifi.ap.setconfig(cfg)
+
+ +

Returns

+

nil

+

Example

+
    wifi.ap.config(ssid, 'password')
+
+ +

See also

+

-

+

+

wifi.ap.getip()

+

Description

+

get ip in ap mode.

+

Syntax

+

wifi.ap.getip()

+

Parameters

+

nil

+

Returns

+

ip address in string, for example:”192.168.0.111”

+

Example

+
    wifi.ap.getip()
+
+ +

See also

+

- wifi.ap.getmac()

+

+

wifi.ap.getmac()

+

Description

+

get mac address in ap mode.

+

Syntax

+

wifi.ap.getmac()

+

Parameters

+

nil

+

Returns

+

mac address in string, for example:”1A-33-44-FE-55-BB”

+

Example

+
    wifi.ap.getmac()
+
+ +

See also

+

- wifi.ap.getip()

+

timer module

+

+

tmr.delay()

+

Description

+

delay us micro seconds.

+

Syntax

+

tmr.dealy(us)

+

Parameters

+

us: delay time in micro second

+

Returns

+

nil

+

Example

+
    -- delay 100us
+    tmr.delay(100)
+
+ +

See also

+

- tmr.now()

+

+

tmr.now()

+

Description

+

return the current value of system counter: uint32, us.

+

Syntax

+

tmr.now()

+

Parameters

+

nil

+

Returns

+

uint32: value of counter

+

Example

+
    -- print current value of counter
+    print(tmr.now())
+
+ +

See also

+

- tmr.delay()

+

+

tmr.alarm()

+

Description

+

alarm time.

+

Syntax

+

tmr.alarm(interval, repeat, function do())

+

Parameters

+

Interval: alarm time, unit: millisecond

+repeat: 0 - one time alarm, 1 - repeat

+function do(): callback function for alarm timed out

+

Returns

+

nil

+

Example

+
    -- print "hello world" every 1000ms
+    tmr.alarm(1000, 1, function() print("hello world") end )
+
+ +

See also

+

- tmr.now()

+

+

tmr.stop()

+

Description

+

stop alarm.

+-Note: only one alarm is allowed, the previous one would be replaced if tmr.alarm() called again before tmr.stop().

+

Syntax

+

tmr.stop()

+

Parameters

+

nil.

+

Returns

+

nil

+

Example

+
    -- print "hello world" every 1000ms
+    tmr.alarm(1000, 1, function() print("hello world") end )
+
+    -- something else
+
+    -- stop alarm
+    tmr.stop()
+
+ +

See also

+

- tmr.now()

+

GPIO module

+

CONSTANT

+

gpio.OUTPUT, gpio.INPUT, gpio.INT, gpio.HIGH, gpio.LOW

+

+

gpio.mode()

+

Description

+

initialize pin to GPIO mode, set the pin in/out mode.

+

Syntax

+

gpio.mode(pin, mode)

+

Parameters

+

pin: 0~11, IO index

+mode: gpio.OUTPUT or gpio.INPUT, or gpio.INT(interrupt mode)

+

Returns

+

nil

+

Example

+
    -- set gpio 0 as output.
+    gpio.mode(0, gpio.OUTPUT)
+
+
+ +

See also

+

- gpio.read()

+

+

gpio.read()

+

Description

+

read pin value.

+

Syntax

+

gpio.read(pin)

+

Parameters

+

pin: 0~11, IO index

+

Returns

+

number:0 - low, 1 - high

+

Example

+
    -- read value of gpio 0.
+    gpio.read(0)
+
+ +

See also

+

- gpio.mode()

+

+

gpio.write()

+

Description

+

set pin value.

+

Syntax

+

gpio.write(pin)

+

Parameters

+

pin: 0~11, IO index

+level: gpio.HIGH or gpio.LOW

+

Returns

+

nil

+

Example

+
    -- set pin index 1 to GPIO mode, and set the pin to high.
+    pin=1
+    gpio.mode(pin, gpio.OUTPUT)
+    gpio.write(pin, gpio.HIGH)
+
+ +

See also

+

- gpio.mode()

+- gpio.read()

+

+

gpio.trig()

+

Description

+

set the interrupt callback function for pin.

+

Syntax

+

gpio.trig(pin, type, function(level))

+

Parameters

+

pin: 0~11, IO index

+type: “up”, “down”, “both”, “low”, “high”, which represent rising edge, falling edge, both edge, low level, high level trig mode separately.

+function(level): callback function when triggered. The gpio level is the param. Use previous callback function if undefined here.

+

Returns

+

nil

+

Example

+
    -- use pin 0 as the input pulse width counter
+    pulse0 = 0
+    du = 0
+    gpio.mode(0,gpio.INT)
+    function pin0cb(level)
+     du = tmr.now() – pulse0
+     print(du)
+     pulse0 = tmr.now()
+     if level == 1 then gpio.trig(0, "down ") else gpio.trig(0, "up ") end
+    end
+    gpio.trig(0, "down ",pin0cb)
+
+
+ +

See also

+

- gpio.mode()

+- gpio.write()

+

PWM module

+

+

pwm.setup()

+

Description

+

set pin to PWM mode. Only 3 pins can be set to PWM mode at the most.

+

Syntax

+

pwm.setup(pin, clock, duty)

+

Parameters

+

pin: 0~11, IO index

+clock: 1~500, pwm frequency

+duty: 0~100, pwm duty cycle in percentage

+

Returns

+

nil

+

Example

+
    -- set pin index 0 as pwm output, frequency is 100Hz, duty cycle is 50-50.
+    pwm.setup(0, 100, 50)
+
+ +

See also

+

- pwm.start()

+

+

pwm.close()

+

Description

+

quit PWM mode for specified pin.

+

Syntax

+

pwm.close(pin)

+

Parameters

+

pin: 0~11, IO index

+

Returns

+

nil

+

Example

+
    pwm.close(0)
+
+ +

See also

+

- pwm.start()

+

+

pwm.start()

+

Description

+

pwm starts, you can detect the waveform on the gpio.

+

Syntax

+

pwm.start(pin)

+

Parameters

+

pin: 0~11, IO index

+

Returns

+

nil

+

Example

+
    pwm.start(0)
+
+ +

See also

+

- pwm.stop()

+

+

pwm.stop()

+

Description

+

pause the output of PWM waveform.

+

Syntax

+

pwm.stop(pin)

+

Parameters

+

pin: 0~11, IO index

+

Returns

+

nil

+

Example

+
    pwm.stop(0)
+
+ +

See also

+

- pwm.start()

+

+

pwm.setclock()

+

Description

+

set pwm frequency for pin.

+-Note: setup pwm frequency will synchronously change others if there are any. Only one PWM frequency can be allowed for the system.

+

Syntax

+

pwm.setclock(pin, clock)

+

Parameters

+

pin: 0~11, IO index.

+clock: 1~500, pwm frequency.

+

Returns

+

nil

+

Example

+
    pwm.setclock(0, 100)
+
+ +

See also

+

- pwm.getclock()

+

+

pwm.getclock()

+

Description

+

get pwm frequency of pin.

+

Syntax

+

pwm.getclock(pin)

+

Parameters

+

pin: 0~11, IO index.

+

Returns

+

number:pwm frequency of pin

+

Example

+
    print(pwm.getclock(0))
+
+ +

See also

+

- pwm.setclock()

+

+

pwm.setduty()

+

Description

+

set duty clycle for pin.

+

Syntax

+

pwm.setduty(pin, duty)

+

Parameters

+

pin: 0~11, IO index

+duty: 0~100, pwm duty cycle in percentage

+

Returns

+

nil

+

Example

+
    pwm.setduty(0, 50)
+
+ +

See also

+

- pwm.getduty()

+

+

pwm.getduty()

+

Description

+

get duty clycle for pin.

+

Syntax

+

pwm.getduty(pin)

+

Parameters

+

pin: 0~11, IO index

+

Returns

+

nil

+

Example

+
    -- D0 is connected to green led
+    -- D1 is connected to blue led
+    -- D2 is connected to red led
+    pwm.setup(0,500,50)
+    pwm.setup(1,500,50)
+    pwm.setup(2,500,50)
+    pwm.start(0)
+    pwm.start(1)
+    pwm.start(2)
+    function led(r,g,b)
+      pwm.setduty(0,g)
+      pwm.setduty(1,b)
+      pwm.setduty(2,r)
+    end
+    led(50,0,0) --  set led to red
+    led(0,0,50) -- set led to blue.
+
+
+ +

See also

+

- pwm.setduty()

+

net module

+

CONSTANT

+

net.TCP, net.UDP

+

+

net.createServer()

+

Description

+

create a server.

+

Syntax

+

net.createServer(type, secure)

+

Parameters

+

type: net.TCP or net.UDP

+secure: true or false, true for safe link, false for ordinary link

+

Returns

+

net.server sub module

+

Example

+
    net.createServer(net.TCP, true)
+
+ +

See also

+

- net.createConnection()

+

+

net.createConnection()

+

Description

+

create a client.

+

Syntax

+

net.createConnection(type, secure)

+

Parameters

+

type: net.TCP or net.UDP

+secure: true or false, true for safe link, false for ordinary link

+

Returns

+

net.server sub module

+

Example

+
    net.createConnection(net.UDP, false)
+
+ +

See also

+

- net.createServer()

+

net.server module

+

+

listen()

+

Description

+

listen on port from [ip] address.

+

Syntax

+

net.server.listen(port,[ip],function(net.socket))

+

Parameters

+

port: port number

+ip:ip address string, can be omitted

+function(net.socket): callback function, pass to Caller function as param if a connection is created successfully

+

Returns

+

nil

+

Example

+
    -- create a server
+    sv=net.createServer(net.TCP, false)
+    -- server listen on 80, if data received, print data to console, and send "hello world" to remote.
+    sv:listen(80,function(c)
+      c:on("receive", function(sck, pl) print(pl) end)
+      c:send("hello world")
+      end)
+
+ +

See also

+

- net.createServer()

+

+

close()

+

Description

+

close server.

+

Syntax

+

net.server.close()

+

Parameters

+

nil

+

Returns

+

nil

+

Example

+
    -- create a server
+    sv=net.createServer(net.TCP, false)
+    -- close server
+    sv:close()
+
+ +

See also

+

- net.createServer()

+

net.socket module

+

+

connect()

+

Description

+

connect to remote.

+

Syntax

+

connect(port, ip)

+

Parameters

+

port: port number

+ip: ip address in string

+

Returns

+

nil

+

See also

+

- net.socket:on()

+

+

send()

+

Description

+

send data to remote via connection.

+

Syntax

+

send(string, function(sent))

+

Parameters

+

string: data in string which will be sent to remote

+function(sent): callback function for sending string

+

Returns

+

nil

+

See also

+

- net.socket:on()

+

+

on()

+

Description

+

register callback function for event.

+

Syntax

+

on(event, function cb())

+

Parameters

+

event: string, which can be: “connection”, “reconnection”, “disconnection”, “receive”, “sent”

+function cb(net.socket, [string]): callback function. The first param is the socket.

+If event is”receive”, the second param is received data in string.

+

Returns

+

nil

+

Example

+
    sk=net.createConnection(net.TCP, false)
+    sk:on("receive", function(sck, c) print(c) end )
+    sk:connect(80,"192.168.0.66")
+    sk:send("GET / HTTP/1.1\r\nHost: 192.168.0.66\r\nConnection: keep-alive\r\nAccept: */*\r\n\r\n")
+
+ +

See also

+

- net.createServer()

+

+

close()

+

Description

+

close socket.

+

Syntax

+

close()

+

Parameters

+

nil

+

Returns

+

nil

+

See also

+

- net.createServer()

+

+

dns()

+

Description

+

get domain ip

+

Syntax

+

dns(domain, function(net.socket, ip))

+

Parameters

+

domain: domain name.

+function (net.socket, ip): callback function. The first param is the socket, the second param is the ip address in string.

+

Returns

+

nil

+

See also

+

- net.createServer()

+

i2c module

+

CONSTANT

+

i2c.SLOW, i2c.TRANSMITTER, i2c. RECEIVER. FAST(400k)is not supported for now.

+

+

i2c.setup()

+

Description

+

initialize i2c.

+

Syntax

+

i2c.setup(id, pinSDA, pinSCL, speed)

+

Parameters

+

id = 0

+pinSDA: 0~11, IO index

+pinSCL: 0~11, IO index

+speed: i2c.SLOW

+

Returns

+

nil

+

See also

+

- i2c.read()

+

+

i2c.start()

+

Description

+

start i2c transporting.

+

Syntax

+

i2c.start(id)

+

Parameters

+

id = 0

+

Returns

+

nil

+

See also

+

- i2c.read()

+

+

i2c.stop()

+

Description

+

stop i2c transporting.

+

Syntax

+

i2c.stop(id)

+

Parameters

+

id = 0

+

Returns

+

nil

+

See also

+

- i2c.read()

+

+

i2c.address()

+

Description

+

setup i2c address and read/write mode.

+

Syntax

+

i2c.address(id, device_addr, direction)

+

Parameters

+

id=0

+device_addr: device address.

+direction: i2c.TRANSMITTER for writing mode , i2c. RECEIVER for reading mode

+

Returns

+

nil

+

See also

+

- i2c.read()

+

+

i2c.write()

+

Description

+

write data to i2c, data can be multi numbers, string or lua table.

+

Syntax

+

i2c.write(id, data1, data2,…)

+

Parameters

+

id=0

+data: data can be numbers, string or lua table.

+

Returns

+

nil

+

Example

+
    i2c.write(0, "hello", "world")
+
+ +

See also

+

- i2c.read()

+

+

i2c.read()

+

Description

+

read data for len bytes.

+

Syntax

+

i2c.read(id, len)

+

Parameters

+

id=0

+len: data length

+

Returns

+

string:data received.

+

Example

+
    id=0
+    sda=1
+    scl=0
+
+    -- initialize i2c, set pin1 as sda, set pin0 as scl
+    i2c.setup(id,sda,scl,i2c.SLOW)
+
+    -- user defined function: read from reg_addr content of dev_addr
+    function read_reg(dev_addr, reg_addr)
+      i2c.start(id)
+      i2c.address(id, dev_addr ,i2c.TRANSMITTER)
+      i2c.write(id,reg_addr)
+      i2c.stop(id)
+      i2c.start(id)
+      i2c.address(id, dev_addr,i2c.RECEIVER)
+      c=i2c.read(id,1)
+      i2c.stop(id)
+      return c
+    end
+
+    -- get content of register 0xAA of device 0x77
+    reg = read_reg(0x77, 0xAA)
+    pirnt(string.byte(reg))
+
+
+ +

See also

+

- i2c.write()

\ No newline at end of file diff --git a/API.md b/API.md new file mode 100644 index 00000000..246622d1 --- /dev/null +++ b/API.md @@ -0,0 +1,1705 @@ +# **nodeMcu API Instruction** # +###version 0.9.2 build 2014-11-18 + +###change log: +2014-11-18
+bug fixed: as a tcp server, the connection can't closed with :close().
+tcp server: inactive connection will closed by server in 30s (previously 180s).
+add a test api node.input() to put lua chunk into lua interpretor, multi-line supported.
+add a test api node.ouput(function) to direct serial output to a callback function.
+file.readline() now returns line include EOL('\n'), and returns nil when EOF. + +2014-11-12
+full version firmware
+ +2014-11-11
+add file.seek() api to file module
+now max 6 pwm channel is supported
+ +2014-11-10
+change log module to file module
+now file operation support multiple read/write
+for now file module only allowed one file opened
+ +2014-11-5
+delete log operation api from node module
+add log module
+modify wifi module api
+modify node.key long_press and short_press default function
+key is triged only when key is released
+ + +# Summary +- Easy to access wireless router +- Based on Lua 5.1.4, Developers are supposed to have experience with Lua Program language. +- Event-Drive programming modal. +- Build-in file, timer, pwm, i2c, net, gpio, wifi module. +- Serial Port BaudRate:9600 +- Re-mapped GPIO pin, use the index to program gpio, i2c, pwm. +- GPIO Map Table: + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
IO indexESP8266 pinIO indexESP8266 pin
0GPIO128GPIO0
1GPIO139GPIO2
2GPIO1410GPIO4
3GPIO1511GPIO5
4GPIO3
5GPIO1
6GPIO9
7GPIO10
+ + +#Burn/Flash Firmware +###Address + +nodemcu_512k.bin: 0x00000
+ +#node module + +## node.restart() +####Description +restart the chip. + +####Syntax + +node.restart() + +####Parameters +nil + +####Returns +nil + +####Example + +``` + node.restart(); +``` + +####See also +**-** []() + + +## node.dsleep() +####Description + +Enter deep sleep mode, wake up when timed out
+ +####Syntax + +node.dsleep(us)
+**-Note:** This function can only be used in the condition that esp8266 PIN32(RST) and PIN8(XPD_DCDC) are connected together. + +####Parameters +us: sleep time in micro second + +####Returns +nil + +####Example + +``` + node.dsleep(us); +``` + +####See also +**-** []() + + +## node.chipid() +####Description +return chip ID + +####Syntax +node.chipid() + +####Parameters +nil + +####Returns +number:chip ID + +####Example + +``` + id = node.chipid(); +``` + +####See also +**-** []() + + +## node.heap() +####Description +return the remain HEAP size in bytes + +####Syntax +node.heap() + +####Parameters +nil + +####Returns +number: system heap size left in bytes + +####Example + +``` + heap_size = node.heap(); +``` + +####See also +**-** []() + + +## node.key() +####Description +define button function, button is connected to GPIO16. + +####Syntax +node.key(type, function()) + +####Parameters +type: type is either string "long" or "short". long: press the key for 3 seconds, short: press shortly(less than 3 seconds)
+function(): user defined function which is called when key is pressed. If nil, cancling the user defined function.
+Default function: long: change LED blinking rate, short: reset chip + +####Returns +nil + +####Example +``` + node.key("long", function(){print('hello world')}) +``` + +####See also +**-** []() + + +## node.led() +####Description +setup the on/off time for led, which connected to GPIO16, multiplexing with node.key() + +####Syntax +node.led(low, high) + +####Parameters +Low: LED off time, LED keeps on when low=0. Unit: milliseconds, time resolution: 80~100ms
+High: LED off time. Unit: milliseconds, time resolution: 80~100ms + +####Returns +nil + +####Example + +``` + -- turn led on forever. + node.led(0); +``` + +####See also +**-** []() + + +## node.input() +####Description +accept a string and put the string into Lua interpretor.
+same as pcall(loadstring(str)) but support multi seperated line. + +####Syntax +node.input(str) + +####Parameters +str: Lua chunk + +####Returns +nil + +####Example + +``` + -- never use node.input() in console. no effect. + sk:on("receive", function(conn, payload) node.input(payload) end) +``` + +####See also +**-** []() + + +## node.output() +####Description +direct output from lua interpretor to a call back function. + +####Syntax +node.output(function(str), serial_debug) + +####Parameters +function(str): a function accept every output as str, and can send the output to a socket.
+serial_debug: 1 output also show in serial. 0: no serial output. + +####Returns +nil + +####Example + +``` + function tonet(str) + sk:send(str) + -- print(str) WRONG!!! never ever print something in this function + -- because this will cause a recursive function call!!! + end + node.ouput(tonet, 1) -- serial also get the lua output. +``` + +####See also +**-** []() + +#file module + +## file.remove() +####Description +remove file from file system. + +####Syntax +file.remove(filename) + +####Parameters +filename: file to remove + +####Returns +nil + +####Example + +``` + -- remove "foo.lua" from file system. + file.remove("foo.lua") +``` + +####See also +**-** [file.open()](#fl_open)
+**-** [file.close()](#fl_close) + + +## file.open() +####Description +open file. + +####Syntax +file.open(filename, mode) + +####Parameters +filename: file to be opened, directories are not supported
+mode:
+ "r": read mode (the default)
+ "w": write mode
+ "a": append mode
+ "r+": update mode, all previous data is preserved
+ "w+": update mode, all previous data is erased
+ "a+": append update mode, previous data is preserved, writing is only allowed at the end of file + +####Returns +nil + +####Example + +``` + -- open 'init.lua', print the first line. + file.open("init.lua", "r") + print(file.readline()) + file.close() +``` + +####See also +**-** [file.close()](#fl_close)
+**-** [file.readline()](#fl_readline) + + +## file.close() +####Description +close the file. + +####Syntax +file.close() + +####Parameters +nil + +####Returns +nil + +####Example + +``` + -- open 'init.lua', print the first line. + file.open("init.lua", "r") + print(file.readline()) + file.close() +``` + +####See also +**-** [file.open()](#fl_open)
+**-** [file.readline()](#fl_readline) + + +## file.readline() +####Description +read one line of file which is opened before. + +####Syntax +file.readline() + +####Parameters +nil + +####Returns +file content in string, line by line, include EOL('\n')
+return nil when EOF. + +####Example + +``` + -- print the first line of 'init.lua' + file.open("init.lua", "r") + print(file.readline()) + file.close() +``` + +####See also +**-** [file.open()](#fl_open)
+**-** [file.close()](#fl_close) + + +## file.writeline() +####Description +write string to file and add a '\n' at the end. + +####Syntax +file.writeline(string) + +####Parameters +string: content to be write to file + +####Returns +true: write ok. +nil: there is error + +####Example + +``` + -- open 'init.lua' in 'a+' mode + file.open("init.lua", "a+") + -- write 'foo bar' to the end of the file + file.writeline('foo bar') + file.close() +``` + +####See also +**-** [file.open()](#fl_open)
+**-** [file.write()](#fl_write) + + +## file.write() +####Description +write string to file. + +####Syntax +file.write(string) + +####Parameters +string: content to be write to file. + +####Returns +true: write ok. +nil: there is error + +####Example + +``` + -- open 'init.lua' in 'a+' mode + file.open("init.lua", "a+") + -- write 'foo bar' to the end of the file + file.write('foo bar') + file.close() +``` + +####See also +**-** [file.open()](#fl_open)
+**-** [file.writeline()](#fl_writeline) + + +## file.flush() +####Description +flush to file. + +####Syntax +file.flush() + +####Parameters +nil + +####Returns +nil + +####Example + +``` + -- open 'init.lua' in 'a+' mode + file.open("init.lua", "a+") + -- write 'foo bar' to the end of the file + file.write('foo bar') + file.flush() + file.close() +``` + +####See also +**-** [file.open()](#fl_open)
+**-** [file.writeline()](#fl_writeline) + + +## file.seek() +####Description +Sets and gets the file position, measured from the beginning of the file, to the position given by offset plus a base specified by the string whence. + +####Syntax +file.seek(whence, offset) + +####Parameters +whence:
+"set": base is position 0 (beginning of the file);
+"cur": base is current position;(default value)
+"end": base is end of file;
+offset: default 0 + +####Returns +success: returns the final file position
+fail: returns nil + +####Example + +``` + -- open 'init.lua' in 'a+' mode + file.open("init.lua", "a+") + -- write 'foo bar' to the end of the file + file.write('foo bar') + file.flush() + file.seek("set") + print(file.readline()) + file.close() +``` + +####See also +**-** [file.open()](#fl_open)
+**-** [file.writeline()](#fl_writeline) + + +## file.list() +####Description +list all files. + +####Syntax +file.list() + +####Parameters +nil + +####Returns +a lua table which contains the {file name: file size} pairs + +####Example + +``` + l = file.list(); + for k,v in l do + print("name:"..k..", size:"..v) + end +``` + +####See also +**-** [file.remove()](#fl_remove) + +#wifi module +##CONSTANT +wifi.STATION, wifi.SOFTAP, wifi.STATIONAP + + +## wifi.setmode(mode) +####Description +setup wifi operation mode. + +####Syntax +wifi.setmode(mode) + +####Parameters +mode: value should be: wifi.STATION, wifi.SOFTAP or wifi.STATIONAP + +####Returns +current mode after setup + +####Example + +``` + wifi.setmode(wifi.STATION) +``` + +####See also +**-** [wifi.getmode()](#wf_getmode) + + + +## wifi.getmode(mode) +####Description +get wifi operation mode. + +####Syntax +wifi.getmode() + +####Parameters +nil + +####Returns +wifi operation mode + +####Example + +``` + print(wifi.getmode()) +``` + +####See also +**-** [wifi.setmode()](#wf_setmode) + + + +## wifi.startsmart() +####Description +starts to auto configuration, if success set up ssid and pwd automatically . + +####Syntax +wifi.startsmart(channel, function succeed_callback()) + +####Parameters + +channel: 1~13, startup channel for searching, if nil, default to 6. 20 seconds for each channel.
+succeed_callback: callback function called after configuration, which is called when got password and connected to AP. + +####Returns +nil + +####Example + +``` + wifi.startsmart(6, cb()) +``` + +####See also +**-** [wifi.stopsmart()](#wf_stopsmart) + + + +## wifi.stopsmart() +####Description +stop the configuring process. + +####Syntax +wifi.stopsmart() + +####Parameters +nil + +####Returns +nil + +####Example + +``` + wifi.stopsmart() +``` + +####See also +**-** [wifi.startsmart()](#wf_startsmart) + + +#wifi.sta module + + +## wifi.sta.config() +####Description +set ssid and password in station mode. + +####Syntax +wifi.sta.config(ssid, password) + +####Parameters + +ssid: string which is less than 32 bytes.
+password: string which is less than 64 bytes. + +####Returns +nil + +####Example + +``` + wifi.sta.config("myssid","mypassword") +``` + +####See also +**-** [wifi.sta.connect()](#ws_connect)
+**-** [wifi.sta.disconnect()](#ws_disconnect) + + + +## wifi.sta.connect() +####Description +connect to AP in station mode. + +####Syntax +wifi.sta.connect() + +####Parameters +nil + + +####Returns +nil + +####Example + +``` + wifi.sta.connect() +``` + +####See also +**-** [wifi.sta.disconnect()](#ws_disconnect)
+**-** [wifi.sta.config()](#ws_config) + + + +## wifi.sta.disconnect() +####Description +disconnect from AP in station mode. + +####Syntax +wifi.sta.disconnect() + +####Parameters +nil + + +####Returns +nil + +####Example + +``` + wifi.sta.disconnect() +``` + +####See also +**-** [wifi.sta.config()](#ws_config)
+**-** [wifi.sta.connect()](#ws_connect) + + + +## wifi.sta.autoconnect() +####Description +auto connect to AP in station mode. + +####Syntax +wifi.sta.autoconnect(auto) + +####Parameters +auto: 0 to disable auto connecting. 1 to enable auto connecting + + +####Returns +nil + +####Example + +``` + wifi.sta.autoconnect() +``` + +####See also +**-** [wifi.sta.config()](#ws_config)
+**-** [wifi.sta.connect()](#ws_connect)
+**-** [wifi.sta.disconnect()](#ws_disconnect) + + + +## wifi.sta.getip() +####Description +get ip address in station mode. + +####Syntax +wifi.sta.getip() + +####Parameters +nil + + +####Returns +ip address in string, for example:"192.168.0.111" + +####Example + +``` + -- print current ip + print(wifi.sta.getip()) +``` + +####See also +**-** [wifi.sta.getmac()](#ws_getmac) + + + +## wifi.sta.getmac() +####Description +get mac address in station mode. + +####Syntax +wifi.sta.getmac() + +####Parameters +nil + + +####Returns +mac address in string, for example:"18-33-44-FE-55-BB" + +####Example + +``` + -- print current mac address + print(wifi.sta.getmac()) +``` + +####See also +**-** [wifi.sta.getip()](#ws_getip) + + +#wifi.ap module + + +## wifi.ap.config() +####Description +set ssid and password in ap mode. + +####Syntax +wifi.ap.config(cfg) + +####Parameters +cfg: lua table to setup ap. + +####Example: + +``` + cfg={} + cfg.ssid="myssid" + cfg.pwd="mypwd" + wifi.ap.setconfig(cfg) +``` + +####Returns +nil + +####Example + +``` + wifi.ap.config(ssid, 'password') +``` + +####See also +**-** []() + + +## wifi.ap.getip() +####Description +get ip in ap mode. + +####Syntax +wifi.ap.getip() + +####Parameters +nil + +####Returns +ip address in string, for example:"192.168.0.111" + +####Example + +``` + wifi.ap.getip() +``` + +####See also +**-** [wifi.ap.getmac()](#wa_getmac) + + + +## wifi.ap.getmac() +####Description +get mac address in ap mode. + +####Syntax +wifi.ap.getmac() + +####Parameters +nil + +####Returns +mac address in string, for example:"1A-33-44-FE-55-BB" + +####Example + +``` + wifi.ap.getmac() +``` + +####See also +**-** [wifi.ap.getip()](#wa_getip) + + +#timer module + +## tmr.delay() +####Description +delay us micro seconds. + +####Syntax +tmr.dealy(us) + +####Parameters +us: delay time in micro second + +####Returns +nil + +####Example + +``` + -- delay 100us + tmr.delay(100) +``` + +####See also +**-** [tmr.now()](#tm_now) + + + +## tmr.now() +####Description +return the current value of system counter: uint32, us. + +####Syntax +tmr.now() + +####Parameters +nil + +####Returns +uint32: value of counter + +####Example + +``` + -- print current value of counter + print(tmr.now()) +``` + +####See also +**-** [tmr.delay()](#tm_delay) + + + +## tmr.alarm() +####Description +alarm time. + +####Syntax +tmr.alarm(interval, repeat, function do()) + +####Parameters +Interval: alarm time, unit: millisecond
+repeat: 0 - one time alarm, 1 - repeat
+function do(): callback function for alarm timed out + +####Returns +nil + +####Example + +``` + -- print "hello world" every 1000ms + tmr.alarm(1000, 1, function() print("hello world") end ) +``` + +####See also +**-** [tmr.now()](#tm_now) + + + +## tmr.stop() +####Description + +stop alarm.
+**-Note:** only one alarm is allowed, the previous one would be replaced if tmr.alarm() called again before tmr.stop(). + +####Syntax +tmr.stop() + +####Parameters +nil. + +####Returns +nil + +####Example + +``` + -- print "hello world" every 1000ms + tmr.alarm(1000, 1, function() print("hello world") end ) + + -- something else + + -- stop alarm + tmr.stop() +``` + +####See also +**-** [tmr.now()](#tm_now) + + +#GPIO module +##CONSTANT +gpio.OUTPUT, gpio.INPUT, gpio.INT, gpio.HIGH, gpio.LOW + + + +## gpio.mode() +####Description +initialize pin to GPIO mode, set the pin in/out mode. + +####Syntax +gpio.mode(pin, mode) + +####Parameters +pin: 0~11, IO index
+mode: gpio.OUTPUT or gpio.INPUT, or gpio.INT(interrupt mode) + +####Returns +nil + +####Example + +``` + -- set gpio 0 as output. + gpio.mode(0, gpio.OUTPUT) + +``` + +####See also +**-** [gpio.read()](#io_read) + + + +## gpio.read() +####Description +read pin value. + +####Syntax +gpio.read(pin) + +####Parameters +pin: 0~11, IO index + +####Returns +number:0 - low, 1 - high + +####Example + +``` + -- read value of gpio 0. + gpio.read(0) +``` + +####See also +**-** [gpio.mode()](#io_mode) + + + +## gpio.write() +####Description +set pin value. + +####Syntax +gpio.write(pin) + +####Parameters +pin: 0~11, IO index
+level: gpio.HIGH or gpio.LOW + +####Returns +nil + +####Example + +``` + -- set pin index 1 to GPIO mode, and set the pin to high. + pin=1 + gpio.mode(pin, gpio.OUTPUT) + gpio.write(pin, gpio.HIGH) +``` + +####See also +**-** [gpio.mode()](#io_mode)
+**-** [gpio.read()](#io_read) + + + +## gpio.trig() +####Description +set the interrupt callback function for pin. + +####Syntax +gpio.trig(pin, type, function(level)) + +####Parameters +pin: 0~11, IO index
+type: "up", "down", "both", "low", "high", which represent rising edge, falling edge, both edge, low level, high level trig mode separately.
+function(level): callback function when triggered. The gpio level is the param. Use previous callback function if undefined here. + +####Returns +nil + +####Example + +``` + -- use pin 0 as the input pulse width counter + pulse0 = 0 + du = 0 + gpio.mode(0,gpio.INT) + function pin0cb(level) + du = tmr.now() – pulse0 + print(du) + pulse0 = tmr.now() + if level == 1 then gpio.trig(0, "down ") else gpio.trig(0, "up ") end + end + gpio.trig(0, "down ",pin0cb) + +``` + +####See also +**-** [gpio.mode()](#io_mode)
+**-** [gpio.write()](#io_write) + + +#PWM module + +## pwm.setup() +####Description +set pin to PWM mode. Only 3 pins can be set to PWM mode at the most. + +####Syntax +pwm.setup(pin, clock, duty) + +####Parameters +pin: 0~11, IO index
+clock: 1~500, pwm frequency
+duty: 0~100, pwm duty cycle in percentage + +####Returns +nil + +####Example + +``` + -- set pin index 0 as pwm output, frequency is 100Hz, duty cycle is 50-50. + pwm.setup(0, 100, 50) +``` + +####See also +**-** [pwm.start()](#pw_start) + + + +## pwm.close() +####Description +quit PWM mode for specified pin. + +####Syntax +pwm.close(pin) + +####Parameters +pin: 0~11, IO index + +####Returns +nil + +####Example + +``` + pwm.close(0) +``` + +####See also +**-** [pwm.start()](#pw_start) + + + +## pwm.start() +####Description +pwm starts, you can detect the waveform on the gpio. + +####Syntax +pwm.start(pin) + +####Parameters +pin: 0~11, IO index + +####Returns +nil + +####Example + +``` + pwm.start(0) +``` + +####See also +**-** [pwm.stop()](#pw_stop) + + + +## pwm.stop() +####Description +pause the output of PWM waveform. + +####Syntax +pwm.stop(pin) + +####Parameters +pin: 0~11, IO index + +####Returns +nil + +####Example + +``` + pwm.stop(0) +``` + +####See also +**-** [pwm.start()](#pw_start) + + + +## pwm.setclock() +####Description + +set pwm frequency for pin.
+**-Note:** setup pwm frequency will synchronously change others if there are any. Only one PWM frequency can be allowed for the system. + +####Syntax +pwm.setclock(pin, clock) + +####Parameters +pin: 0~11, IO index.
+clock: 1~500, pwm frequency. + +####Returns +nil + +####Example + +``` + pwm.setclock(0, 100) +``` + +####See also +**-** [pwm.getclock()](#pw_getclock) + + + +## pwm.getclock() +####Description +get pwm frequency of pin. + +####Syntax +pwm.getclock(pin) + +####Parameters +pin: 0~11, IO index. + +####Returns +number:pwm frequency of pin + +####Example + +``` + print(pwm.getclock(0)) +``` + +####See also +**-** [pwm.setclock()](#pw_setclock) + + + +## pwm.setduty() +####Description +set duty clycle for pin. + +####Syntax +pwm.setduty(pin, duty) + +####Parameters +pin: 0~11, IO index
+duty: 0~100, pwm duty cycle in percentage + +####Returns +nil + +####Example + +``` + pwm.setduty(0, 50) +``` + +####See also +**-** [pwm.getduty()](#pw_getduty) + + + +## pwm.getduty() +####Description +get duty clycle for pin. + +####Syntax +pwm.getduty(pin) + +####Parameters +pin: 0~11, IO index + +####Returns +nil + +####Example + +``` + -- D0 is connected to green led + -- D1 is connected to blue led + -- D2 is connected to red led + pwm.setup(0,500,50) + pwm.setup(1,500,50) + pwm.setup(2,500,50) + pwm.start(0) + pwm.start(1) + pwm.start(2) + function led(r,g,b) + pwm.setduty(0,g) + pwm.setduty(1,b) + pwm.setduty(2,r) + end + led(50,0,0) -- set led to red + led(0,0,50) -- set led to blue. + +``` + +####See also +**-** [pwm.setduty()](#pw_setduty) + + +#net module +##CONSTANT +net.TCP, net.UDP + + +## net.createServer() +####Description +create a server. + +####Syntax +net.createServer(type, secure) + +####Parameters +type: net.TCP or net.UDP
+secure: true or false, true for safe link, false for ordinary link + +####Returns +net.server sub module + +####Example + +``` + net.createServer(net.TCP, true) +``` + +####See also +**-** [net.createConnection()](#nt_createConnection) + + + +## net.createConnection() +####Description +create a client. + +####Syntax +net.createConnection(type, secure) + +####Parameters +type: net.TCP or net.UDP
+secure: true or false, true for safe link, false for ordinary link + +####Returns +net.server sub module + +####Example + +``` + net.createConnection(net.UDP, false) +``` + +####See also +**-** [net.createServer()](#nt_createServer) + + +#net.server module + +## listen() +####Description +listen on port from [ip] address. + +####Syntax +net.server.listen(port,[ip],function(net.socket)) + +####Parameters +port: port number
+ip:ip address string, can be omitted
+function(net.socket): callback function, pass to Caller function as param if a connection is created successfully + +####Returns +nil + +####Example + +``` + -- create a server + sv=net.createServer(net.TCP, false) + -- server listen on 80, if data received, print data to console, and send "hello world" to remote. + sv:listen(80,function(c) + c:on("receive", function(sck, pl) print(pl) end) + c:send("hello world") + end) +``` + +####See also +**-** [net.createServer()](#nt_createServer) + + + +## close() +####Description +close server. + +####Syntax +net.server.close() + +####Parameters +nil + +####Returns +nil + +####Example + +``` + -- create a server + sv=net.createServer(net.TCP, false) + -- close server + sv:close() +``` + +####See also +**-** [net.createServer()](#nt_createServer) + + +#net.socket module + +## connect() +####Description +connect to remote. + +####Syntax +connect(port, ip) + +####Parameters +port: port number
+ip: ip address in string + +####Returns +nil + +####See also +**-** [net.socket:on()](#nk_on) + + + +## send() +####Description +send data to remote via connection. + +####Syntax +send(string, function(sent)) + +####Parameters +string: data in string which will be sent to remote
+function(sent): callback function for sending string + +####Returns +nil + +####See also +**-** [net.socket:on()](#nk_on) + + + +## on() +####Description +register callback function for event. + +####Syntax +on(event, function cb()) + +####Parameters +event: string, which can be: "connection", "reconnection", "disconnection", "receive", "sent"
+function cb(net.socket, [string]): callback function. The first param is the socket.
+If event is"receive", the second param is received data in string. + +####Returns +nil + +####Example + +``` + sk=net.createConnection(net.TCP, false) + sk:on("receive", function(sck, c) print(c) end ) + sk:connect(80,"192.168.0.66") + sk:send("GET / HTTP/1.1\r\nHost: 192.168.0.66\r\nConnection: keep-alive\r\nAccept: */*\r\n\r\n") +``` + +####See also +**-** [net.createServer()](#nt_createServer) + + + +## close() +####Description +close socket. + +####Syntax +close() + +####Parameters +nil + +####Returns +nil + +####See also +**-** [net.createServer()](#nt_createServer) + + + +## dns() +####Description +get domain ip + +####Syntax +dns(domain, function(net.socket, ip)) + +####Parameters +domain: domain name.
+function (net.socket, ip): callback function. The first param is the socket, the second param is the ip address in string. + +####Returns +nil + +####See also +**-** [net.createServer()](#nt_createServer) + + +#i2c module +##CONSTANT +i2c.SLOW, i2c.TRANSMITTER, i2c. RECEIVER. FAST(400k)is not supported for now. + + +## i2c.setup() +####Description +initialize i2c. + +####Syntax +i2c.setup(id, pinSDA, pinSCL, speed) + +####Parameters +id = 0
+pinSDA: 0~11, IO index
+pinSCL: 0~11, IO index
+speed: i2c.SLOW + +####Returns +nil + +####See also +**-** [i2c.read()](#ic_read) + + + +## i2c.start() +####Description +start i2c transporting. + +####Syntax +i2c.start(id) + +####Parameters +id = 0 + +####Returns +nil + +####See also +**-** [i2c.read()](#ic_read) + + + +## i2c.stop() +####Description +stop i2c transporting. + +####Syntax +i2c.stop(id) + +####Parameters +id = 0 + +####Returns +nil + +####See also +**-** [i2c.read()](#ic_read) + + + +## i2c.address() +####Description +setup i2c address and read/write mode. + +####Syntax +i2c.address(id, device_addr, direction) + +####Parameters +id=0
+device_addr: device address.
+direction: i2c.TRANSMITTER for writing mode , i2c. RECEIVER for reading mode + +####Returns +nil + +####See also +**-** [i2c.read()](#ic_read) + + +## i2c.write() +####Description +write data to i2c, data can be multi numbers, string or lua table. + +####Syntax +i2c.write(id, data1, data2,...) + +####Parameters +id=0
+data: data can be numbers, string or lua table. + +####Returns +nil + +####Example + +``` + i2c.write(0, "hello", "world") +``` + +####See also +**-** [i2c.read()](#ic_read) + + + +## i2c.read() +####Description +read data for len bytes. + +####Syntax +i2c.read(id, len) + +####Parameters +id=0
+len: data length + +####Returns +string:data received. + +####Example + +``` + id=0 + sda=1 + scl=0 + + -- initialize i2c, set pin1 as sda, set pin0 as scl + i2c.setup(id,sda,scl,i2c.SLOW) + + -- user defined function: read from reg_addr content of dev_addr + function read_reg(dev_addr, reg_addr) + i2c.start(id) + i2c.address(id, dev_addr ,i2c.TRANSMITTER) + i2c.write(id,reg_addr) + i2c.stop(id) + i2c.start(id) + i2c.address(id, dev_addr,i2c.RECEIVER) + c=i2c.read(id,1) + i2c.stop(id) + return c + end + + -- get content of register 0xAA of device 0x77 + reg = read_reg(0x77, 0xAA) + pirnt(string.byte(reg)) + +``` + +####See also +**-** [i2c.write()](#ic_write) + diff --git a/README.html b/README.html deleted file mode 100644 index 686520a1..00000000 --- a/README.html +++ /dev/null @@ -1,1126 +0,0 @@ -README

NodeMcu

-

A lua based firmware for wifi-soc esp8266

-

version 0.9.2 2014-11-12

-

Summary

-
    -
  • Easy to access wireless router
  • -
  • Based on Lua 5.1.4
  • -
  • Event-Drive programming preferred.
  • -
  • Build-in file, timer, pwm, i2c, net, gpio, wifi, and system api.
  • -
  • GPIO pin re-mapped, use the index to access gpio, i2c, pwm.
  • -
  • GPIO Map Table:
  • -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - -
IO indexESP8266 pinIO indexESP8266 pin
0GPIO128GPIO0
1GPIO139GPIO2
2GPIO1410GPIO4
3GPIO1511GPIO5
4GPIO3
5GPIO1
6GPIO9
7GPIO10
- -

Flash the firmware

-

nodemcu_512k.bin: 0x00000

-for most esp8266 modules, just pull GPIO0 down and restart.

-

Connect the hardware in serial

-

braudrate:9600

-

Start play

-

Connect to your ap

-
    print(wifi.sta.getip())
-    --0.0.0.0
-    wifi.setmode(wifi.STATION)
-    wifi.sta.config("SSID","password")
-    print(wifi.sta.getip())
-    --192.168.18.110
-
- -

Manipulate hardware like a arduino

-
    pin = 1
-    gpio.mode(pin,gpio.OUTPUT)
-    gpio.write(pin,gpio.HIGH)
-    print(gpio.read(pin))
-
- -

Write network application in nodejs style

-
    -- A simple http client
-    conn=net.createConnection(net.TCP, false) 
-    conn:on("receive", function(conn, payload) print(c) end )
-    conn:connect(80,"115.239.210.27")
-    conn:send("GET / HTTP/1.1\r\nHost: www.baidu.com\r\n"
-        .."Connection: keep-alive\r\nAccept: */*\r\n\r\n")
-
- -

Or a simple http server

-
    -- A simple http server
-    srv=net.createServer(net.TCP) 
-    srv:listen(80,function(conn) 
-      conn:on("receive",function(conn,payload) 
-        print(payload) 
-        conn:send("<h1> Hello, NodeMcu.</h1>")
-      end) 
-    end)
-
- -

Do something shining

-
  function led(r,g,b) 
-    pwm.setduty(0,r) 
-    pwm.setduty(1,g) 
-    pwm.setduty(2,b) 
-  end
-  pwm.setup(0,500,50) 
-  pwm.setup(1,500,50) 
-  pwm.setup(2,500,50)
-  pwm.start(0) 
-  pwm.start(1) 
-  pwm.start(2)
-  led(50,0,0) -- red
-  led(0,0,50) -- blue
-
- - -
  lighton=0
-  tmr.alarm(1000,1,function()
-    if lighton==0 then 
-      lighton=1 
-      led(50,50,50) 
-    else 
-      lighton=0 
-      led(0,0,0) 
-    end 
-  end)
-
- -

If you want to run something when system started

-
  --init.lua will be excuted
-  file.open("init.lua","w")
-  file.writeline([[print("Hello, do this at the beginning.")]])
-  file.close()
-  node.restart()  -- this will restart the module.
-
- -

Check this out

-

Tencent QQ group: 309957875
-nodemcu wiki
-nodemcu.com comming soon~~~

\ No newline at end of file diff --git a/README.md b/README.md index 28f7411b..0de7844c 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,7 @@ # **NodeMcu** # ###A lua based firmware for wifi-soc esp8266 -version 0.9.2 2014-11-12 +version 0.9.2 build 2014-11-18 +[change log](https://github.com/funshine/nodemcu-firmware/wiki/nodeMcu:-lua-based-interactive-firmware-for-mcu#change_log) # Summary - Easy to access wireless router @@ -136,4 +137,4 @@ braudrate:9600 #Check this out Tencent QQ group: 309957875
[nodemcu wiki](https://github.com/funshine/nodemcu-firmware/wiki/nodeMcu:-lua-based-interactive-firmware-for-mcu)
-[nodemcu.com](http://www.nodemcu.com) comming soon~~~ \ No newline at end of file +[nodemcu.com](http://www.nodemcu.com) \ No newline at end of file