From c4d2144d0d77930c619c4a118f32f5d4c56491b3 Mon Sep 17 00:00:00 2001 From: ncpfs archive import Date: Tue, 28 Apr 2026 20:39:58 +0200 Subject: [PATCH] Import ncpfs 2.0.7 --- .downloads/ncpfs-2.0.7.tgz | Bin 0 -> 148822 bytes Changes | 8 + FAQ | 2 +- Makefile | 43 +- TODO | 5 +- {util => bin}/nwbpsecurity | 0 {util => bin}/start_ipx | 0 {util/com_err => include}/com_err.h | 0 {util => include}/ipxlib.h | 0 {util => include}/ncplib.h | 4 + ipx-1.0/Gregs.Makefile | 24 - ipx-1.0/Makefile | 19 +- lib/Makefile | 76 + {util => lib}/com_err/ChangeLog | 0 {util => lib}/com_err/Makefile | 7 +- {util => lib}/com_err/com_err.3 | 0 {util => lib}/com_err/com_err.c | 0 lib/com_err/com_err.h | 40 + {util => lib}/com_err/com_err.texinfo | 0 {util => lib}/com_err/compile_et | 0 {util => lib}/com_err/compile_et.1 | 0 {util => lib}/com_err/error_message.c | 0 {util => lib}/com_err/error_table.h | 0 {util => lib}/com_err/et_c.awk | 0 {util => lib}/com_err/et_h.awk | 0 {util => lib}/com_err/et_name.c | 0 {util => lib}/com_err/init_et.c | 0 {util => lib}/com_err/internal.h | 0 {util => lib}/com_err/mit-sipb-copyright.h | 0 {util => lib}/ipx_sap_types | 0 {util => lib}/ncplib.c | 385 +--- {util => lib}/ncplib_err.et | 0 {util => lib}/nwcrypt.c | 0 man/ncopy.1 | 8 +- man/ncpmount.8 | 2 +- man/nprint.1 | 2 +- man/nwauth.1 | 69 + man/nwsfind.1 | 36 + man/pqlist.1 | 2 +- man/pserver.1 | 11 +- man/slist.1 | 2 +- ncpfs-2.0.6.lsm => ncpfs-2.0.7.lsm | 8 +- sutil/Makefile | 42 + sutil/ipxlib.h | 93 + sutil/ncplib.c | 1927 ++++++++++++++++++++ sutil/ncplib.h | 198 ++ {util => sutil}/ncpmount.c | 0 {util => sutil}/ncpumount.c | 13 + sutil/nwcrypt.c | 209 +++ sutil/nwsfind.c | 102 ++ util/Makefile | 71 +- util/com_err.h | 1 - util/nwauth.c | 127 ++ util/pserver.c | 70 +- 54 files changed, 3169 insertions(+), 437 deletions(-) create mode 100644 .downloads/ncpfs-2.0.7.tgz rename {util => bin}/nwbpsecurity (100%) rename {util => bin}/start_ipx (100%) rename {util/com_err => include}/com_err.h (100%) rename {util => include}/ipxlib.h (100%) rename {util => include}/ncplib.h (99%) delete mode 100644 ipx-1.0/Gregs.Makefile create mode 100644 lib/Makefile rename {util => lib}/com_err/ChangeLog (100%) rename {util => lib}/com_err/Makefile (74%) rename {util => lib}/com_err/com_err.3 (100%) rename {util => lib}/com_err/com_err.c (100%) create mode 100644 lib/com_err/com_err.h rename {util => lib}/com_err/com_err.texinfo (100%) rename {util => lib}/com_err/compile_et (100%) rename {util => lib}/com_err/compile_et.1 (100%) rename {util => lib}/com_err/error_message.c (100%) rename {util => lib}/com_err/error_table.h (100%) rename {util => lib}/com_err/et_c.awk (100%) rename {util => lib}/com_err/et_h.awk (100%) rename {util => lib}/com_err/et_name.c (100%) rename {util => lib}/com_err/init_et.c (100%) rename {util => lib}/com_err/internal.h (100%) rename {util => lib}/com_err/mit-sipb-copyright.h (100%) rename {util => lib}/ipx_sap_types (100%) rename {util => lib}/ncplib.c (91%) rename {util => lib}/ncplib_err.et (100%) rename {util => lib}/nwcrypt.c (100%) create mode 100644 man/nwauth.1 create mode 100644 man/nwsfind.1 rename ncpfs-2.0.6.lsm => ncpfs-2.0.7.lsm (83%) create mode 100644 sutil/Makefile create mode 100644 sutil/ipxlib.h create mode 100644 sutil/ncplib.c create mode 100644 sutil/ncplib.h rename {util => sutil}/ncpmount.c (100%) rename {util => sutil}/ncpumount.c (95%) create mode 100644 sutil/nwcrypt.c create mode 100644 sutil/nwsfind.c delete mode 120000 util/com_err.h create mode 100644 util/nwauth.c diff --git a/.downloads/ncpfs-2.0.7.tgz b/.downloads/ncpfs-2.0.7.tgz new file mode 100644 index 0000000000000000000000000000000000000000..5ddb7a0d5b45ec73b3ef79010fd9a26238efb105 GIT binary patch literal 148822 zcmV(s-kI0z9n|;gKX2b&f1bnlGn*o z3gmz!;<@k)W<>Gd@7LYH42Gnfvs;@y?1q(C5@!bJZuI5r%apU#+&?}UAB|r=dGIHF z^s}Rv&!6iDTI-iDnt;4k>JzA?4d4+{H7 z_u1M%_&@h4lk6wPiLRcZccB`F3zvDEA`dn^xfylSYKC#)rDIu8$GK^?=oAf zW@!t06e~^Jg&!;Rro~!ITU%}Le{D^kZ}h6JrnxOVu3&vx1CPwzoy}+qJfP=o)7BO% zJpSMPDD^9Nls)a;%GS=7GYe*C-`bVe)m*bB=-Vo93+u=FtkFxeTG`TT>sNN>hy~S_ z;8!oPj4o}nuIg{Psm*-uW+Poz4ZfUN?@jH%ZdKx+v&&!N9avMFf^Jg=av*`#7Bb0N z5YjB2j{?Gzy4dK#%$BaSBke1F_Nc&*y2gTfW=dWptF$RMc(7b(Gp$(SrWxz6OIvE+ z&X(E){vszMKIo;n<<0%FrA5{v_*qq~a@$z#R(E)M>NmatDbtP4EWYPW@|>@_va$8t zfYT8KQdDi(T^%15w#*8@Abr9KJ;7H`%=|a}7|$TV0-O+KBp0veRc&u^ zo^B4I<~g)*?V6=3t8z*={QD6d*}DsUesQD! zf&+juL5@0XrVm(zg{l2-<=XOz=WATZQmdaWO}VgoJRTp8AmZBoj^+6lJds1YO4DFr z1wxsmK)d$PnmqEz+Zx@L?k?Q5s-T+WqOhiS(C3X35$dBq!=s$d*`5#?^e0!gclvmI zGQI;tC4FBHI|ysio{%DP=O`iMU#SQNJ5#RD5Xbqx-qtTqtg2yVLR zEFLQ?Ol)^#;+$ouQ}aL}2d5JLWOHdgxH&x@DO^=IR~KD`C_d25Pk?Xm@a z{d}sAPL7{qgD=;oN>32FHx$4KIoY~!4Tq2lj%~H!z|%)ajeDoqzMzW^UY8IbLzCRi z5XBH%s~KWS*#zH60g50Bye4iUXh%+XZ8HRtA4DdXfVBm}DTKf%B&@`+0s+Z4z#D;k z`aiSYElQ!VG2igz+H5#bs5wNHRfT{uz8}Pg80iqu^qUREVBkm(`Y1^9f!Wg5CfAqk z6kDrLff469767R7R*Tluz)#jnO#0qdbWKH?A3vtxOLTewa^AFK2V2m+5`YO5HeR!R zj7bvCt08GRl7`TiL-?A*I^@G=V27HbdQExc6A6~g4FIpMD3}reT-1Qm0Eo15+bpY^ zkV*kPz@4h~a(p1^fO8gk>^`j=FgL59E)d^zqoS}sxoK?xzwhD9l>kd78y{*-c?Lmr zVs@j27#4k?7%04{sxfH|BXxiz@Xq*X^vo{#ukM zF88gh*4?_ur5XlHoKAT@otugtZGcS0blA&zK9$lYvZRCt=OFNymxnN>E>loea!({o zTe7K#O=Kk^oKzZ^o-b8&Dz)VdlNgk{#sS3*cY#U!+%&xS%+?KZD7s@s8Tr)Zu5rN+ z(aIuGwf96*Nsfr3ApWAt+?>>xMM24#y)%RtNAZrm%Z0Qvh#az7S~5F@zZ%X118ARH zE6Heq_^TH#=pVGhVW|?rA-~c~f#s@V_Bs|T<7c_CF+H%D$zWwa|)H{ z=VF$A=u3BvcNi4z*MV zCx?(9>^!JR5}DRZ2ceRTJYUT10%pz;&vQf$A#aqPFxGs+VTg}0-H)k0%{?SUXJHMU z7`x9$KC(iqlCgjxQTUjGv$TW4DHgbmQJ70308?e=yQ2_yT2cyMQxw|pmdxEC*x(?} z<~uQliFfRWId!L9Z0;o(tbh=3iSWeQs^BerszD$(92tmNN9B<6M~LaPV}&DerOBzz zA}mpm>1tJorBb3{GB}8MN#tk&xaORWzA6W6sSuASg<0w=Qcrk*ucdNMw@^&y1*+VxgNewl*h)hHe@BL>RI_(VKB_n$QVS7aTJy4@*zop6G#E77)@pn-WsXm70kP5mK2#?_n2)#qz{dj3woy*Ph&CNF?9CUt#5aDvcz5>x>@C+slpnnzdB|)xk78ux**lva;ZoJBE{pP0&Fo2^-p$PPZj zGr|$fA>vW@0By+NeU`Ubs6|p$H+O)v;c}_s$>@ja?hgrhPRNx9%U~C0vJ9Yr&BW`6 zh#e1MD5r4mw*nBVAXfrb_u0jONd}VyJbQ#J+7Z;@wYXSDWo<*v0d~qBt4CEaxmjDaK9}9$bJ&*~t_iNl&=Fw3 z1Y?9iWO|qCEiHJSz{D&!u7FfPbd3D3^*3u*WD=wS0o^Hi%*TjD_=nQtfhUyAk4wW- z&s`geW#Fw_TG2fWBK!O>0RltOK@pgh=-9$O%H&i+7u?q0Jr0c{Iwi?;7`z4?16RA; zcq+pNy%uAR>6+{$0B;jkF##u5tKeaX=MEkv_=|$>UChiQXlBhh=`|Jy3xlDtp|%P7`WWa- z=oRBipxR7oGn^f8tHMwif}aV@!_mUQCOM&ql5~_Wa?cQJM=wkkL8`}(Ckrx2483Hj zG1VC&ZB5>S6GKqv$jR4qC;&>N(4tReS+(#kR0Iq`n2loK@$_DgXLy0|#r?U@0byF? zFQbUSI{gS%AaryO9QFkZuCB4gC$QeePAE&8kBe8>Hkc4bZJx*YMayYUb}N1B?0U;5 z@+v*TJDA+fEW4{$6krD-yYV)k$C_h21JK4xP^^=-c+>#_Cku$uNq$7Y z(7mQP;W1Mp6^!2SG(` z2Nia#Dc}r2OV)@Oni10} zzZVLC=d+Sh3n$&2f~R~I3zAY?Hsn0Q2T5h$LTVdpv4i92DK90H6&9v7xGw zSOuTn^C#H1_d?S;`oDxaaht5ul%?#Aa!OK$!XFw&hU{g}kfCPH{bULFM0D>#f-|jTJNuXI( zOHG*rVHihxOu?Lp6advHA){dP(Q4E2l>3pO#F`;He8A!GW>~E%WT2{zg`vJkNI^%? z*lUPz)FHB6&P-=d47o@8*5po>gUoVx=Z5QV!q>){nj1BJTEPH`9l~Z50C_-ACAG7p z04hjf53p=~SWfjO5COG2XLDUr7A zlsjS>fr1`A-_e(1tv@zi=C=c=rqen~%ORIq$~*eHoyO=e73l-I5ONtb$mYFMk&2km z!fio0j-rd4bQ3k>LZx5T)UNYlqq1V7{7=(7wTjTd#FO5=OzUX zJxAd3BM$zSgihE_g&|H#ss+rBcKAungKbVMtj7$bMN$Zoa?Ob5Yx9U-Q`9oR5=u0cwAbFPsE{i&)Dr5WJ5Qhr zbu+2J1g%&#iZRZb(O`A&_V@2j{*(GjqJuKI*ism1LNKE!;^-g;ea}5)sm>0gfC)l# zQ>b&UQnO-V#5Ox0FV9y7gqG9NB(rlAda@B0*VBS$tvKy@?)d}Mk>})&s2^6!6Qx9`NDZZ3#hppUD z(t``X=U}KF)cEb*hs@sayk|eDOHI0^o4Q6y^|@Jh-TROz?(!q+Ah=Z2o1Si@F~;?Z z0l?lW-XDYlkTW~E;KuVIGO3zsV ziBiO|@uqn=&)7epdW}AiZgb(nY+>kE!(3bI4@WA|LI%SuM^*&Vor5s{LQDx&{3Zkl zN4gw0?mhKkjMFsg2Qz5`((ks|vXPOr+r*YBTu||o_U%IB{m;tCMVNo$*GZC^eihKT zr>PyNmv=>*!%VF-i==^p7_tbsviJHbZQCT%dY0b!V1E0@Lg?Q)M1tN?G4HXx(DvV* zOfvCwyXl##%>~HGjHs@w4bp_oV;(6;j61;zaThp0fxQ)v;Z$9NEworNgoPQ6XmHuS z`wM9#qYCgLEVAd}#3GD*k}`m*DBdZAq+JsVQE8mx+ot3UsiR&~(CW%Te8}G+Uoc$K z^w}v$;n$_j2}w&bOp|n_7^P*DC!v>@AY+`hxq+v3^{g#Cdu{P>QZ%Wz{Ta&9{fU*=7Qt7tTK|LFk+*WPP9&As|4JXrv_{@Ka)hE*@z8|ZgLO)b> z6RKxiu8V_up;jk_1J`UqH%M_cTkd>4+C_IM*4bZ6o{1ZlWtxjxWNz!#St$n$C&VD%W6_J<&iid zly;%&J`XspLy|a!80@VWz|`(WD~YPU*{wTL67kbGHrKZ66i>p`>z2oIJ{g~&_CXvD z<;18arxmhO(v@EOr<=aBmFDTa#MJGwc>5JOlI_}=ek<(D~ zt-OfgRXF>5M$!cX5Q-&p!cVYwO}wRRu@(m-2|nyIiQF<0?FVyEJjB~^;N1j(h=f}TQE(2G2S6BC-(E9 zF*oLF&YZLLt$TM832~LlKwXHm56OAcpjI7Mc$mH*OFkyfX!OPNq<}gE)Nx2Gb_gR; zRUM}W23y4g?#J{<9n>Cm*x|izXowIt`$VwSB-?Z|ELFt$@ezIlb}u#i-pP>BrK52K zk8uVyu@1%xJM$+z3n%_JokI1Ye>bq;El@3*#yw&(F*}S8D$LLmeD5>q01dk+(Dfrz zH}?mU-`egzdwtEXaKu-O6~}|F$mqL?=kS^a1u>R8*DzptQ2DHf*!I>1Ta*9j9X7>GxNYiN1KR-+ny3`Y;*M zeOD8@BVCJTWRnGO*9HGQ`Q>JEexolZSD(*rZm`;$U-jwbB^Ez@^J$_#oqmNhC%?R% zT;AxfA1CMPf|mb!270b&ZH_pAC>lr@P3G9W;U9m#frC1f*^ zkS<7ZaveWR3mU0opcxu0D-++}{+^|(x~dmI@{-JqbnnDcb?tTPY;~4a7WdK=d7K;MmHm~kCGHk$iK=Lcj6`~rGFcXEoZ0P{RMp{-GM zRqrqv=-)Z6w_yL8XSElNqXrC#mcxgQvnC8d_Qf@x`TqG)4Hj|UIz4IEQGbJ52%W%& zw;JsqMXl|~js2hVn(hd87y3A^HTUVDVh4%K6~COEBh`R)A01!?M^(U$s*8jAVSWFs z@e>>`)P!N$=f`!q-|aKnpra$vtnb5oYpq{IyWaY#v5))UwCbm|25djtNVi(p%Sn@Q zOSOcD2T)S~31Q&8d4#KN)&J)l){_DW*hlRpKpSqRaqiCR1`LiT6hHg|HGvP&;r{|) zbRv#xzp!EUFA_Xpn%Z*Ph6(_R2s&#oPH+!ize z4E_)?QaJ8@owt(5R&*8E)nsg`*u9t3e zqjjL}6YaA&tTm3#TL~D0kxyU?u}gwAeIN?R+W7*(fM^`TQ2Vds=?UxB{vuw%QM{-_ zwc5c?4a7V=jsth0-H>~7B72bgNQjMmO<{dhKgEC_ZU1W+Hlyc%*hM8S(t#Suq^xH> zBQ5|6e?hd{1eQnAx)9-5(#IZ<*Fi7_5-oY6$ePmda+9`tl4M?z7f3jDKoVhP*(}sl zhy^?;ccb8dDh1L^U!kDEtPfke6D9Jej!hAm5^A>{G*7ZroQ6ZFelk`{MCBK!6tmN* zD<7UB21%Rr2Ii9~axo+jg>E00hBMZ!hpIAJ`O!-gevvON_&%szM%fRAEeC;3c<Z~CdXvRgI!S{;T5SNKr#&34GiDArau8!H%4xdEXPUQhWSt#ayrZ_*%Vw4$X9{*F zSA!fy4`S3y&bE}!Cwb^n`UaTKu~HPfLd%}1+-1dh!KH%3EU?K42sMhpBO+2neouR0 z$mc>*@easpP?>cCvyENEX*F!_5~RBA5tKOE$tXjZqoX2EUX-;$xpY*nn@}AYQ&_el z*&Rz03F9d<+RHtZX#vvbvBA_n?%Q8j(uE(LQP55awF0JD2x`t4-I6r{dsZTY?4fnq zBpAW`*#(ed*1&$Ss?)O2uq;vw3KuFz5*N2^qK$Yl1`DgN$>0&{5he=Ri^8&Pg$v_J z3#ykRV5;9UH?P2X2bPv{ckP>-Xx$AkWDlJ{?M3_K2)K=-UrbJUk03xEzL?$sIRAsZ zRj=1d(ItrA{)o;H;`atP4oCm7kOB1|eW$d(NQq#3=5XCLb0Q@+Rk^wuqhLqxT9K8v znjg(Ux0cYVJZ&v+5=(B(^fx={(^HCk{fNd>p?E;dMTLfpltXeEX%q}+r_`xQ-zC<} z(`~=-oM8Z67P~NmccjP|dZQU^m^TcIMa0@9Jcl!%UvjmNzw{cBizQ<`bU&sl9^jAQ z2AbuRr@J;kmaT{0Brn)^d*XyBvJd!eW5gEh__&OYbCEJGa=BTJJW~{};rAUCmJB^K zUrEb!7wsm-10WG(HAQU@OxeHUm*6Jo-C*=FzR^hkE^hQdY!4JofNltKBNE}t!J(sn z7;wIZ4`O5^2)8k07v4}v%M>(x3G-Ts27~<_XCq!wBrrmFPuX+?oxK4{&TinQ1*7K$ zQ31Ye;tweL2r?-Ap@0!OLSOlG{R9vsHMto`R_j&dOHriLK=?7wm$Vs<;rXhA4CrUI ziHV9_e3X?@$^h9=C<(2Uag;qcd1NAzXUas+jXV=zD#)749MRCEhuRLsk)1205hI0b zWfrR3xO>37DUX?y=oU_Tbc>`i^FDske^mS@;`+m{9RI2ExUyY|#eb?o;eGt4ukq91 z7m^F_(v_|yBq|X;Vb~~_NF_r^ZB5zx0;*^3nqGk%^_)=9;zr-+cV4nj>`%v~%j@1{ z30S8M5EnKE7%p#P2*hNA2HAja0K-SXxFd?sg#nvR5hU<2Vns5X0fItrJM@e^qo-39 zI};8w9+DU{9_m8(Eny4bttzW3QE2VI6IGkQSdaF&3! zf!7iHB$o5*HK5rIeEu&9Xxo;aGyG}h_qYYUrQmNo3o*J5c~=7Aja(_#vyVLDVjc^{ zW3&^HQb*`bk@z?)RB^XZhGR^EU~28zw!LRNdhv?c?RjiktDH3So{?nKV3XG?Z!nhR zB#@E`K?DW|)>?mxtHCh^CA&r^s$!zDMGqQTj#0?QJ~-l)4&jN0ac6*T-jVfFV4jpa zA_iZ1e3Mjwa~WNaFW$R@nc$>Q=extfk%6EdMf z&K>78{r~`j%O>x@KE4bK;x! z#J6xx(pOi>RwLvmuX_?!=y$RZQ|0L01Z);FOE8O;*L&qo&3PUp(6m{{@N`H)940@E z$WZ;J1i<#3ADK`sM7H$^*sipm1Z0F8bqeRO_Uq(V;C1Q6YjiyfG2W)f{;W|1T2%M= z(l7~K7#+d>4QN4R&gs;fPH^*j6F8+VaO0OH@zYryA^qu3wdMgT;(vJGg_~D;-z|0D z&!(mB@6V$+J91u)AzBVg6jeVu6zT}6CKiOVG1>{4W1nBcy~o(E=t}YQA{hMu68Jlm zz)SwSafv)z-j$|T#hyDs%bea6F#Pk92~>jI=)BoW7H^)Fn*F|S^;v!7^f9G4c@Vs;!g2Z5DyCbc!IKYJJ2Dn6uXQk zM>-PPFoHL^Tfjz-fywU?uAv~X(1VQosx@5PbCHzCz9Jy~ksMvBRpfjtur79|kS-*+ z8w0!!h(tYlBiCry2xP5Z+Y999D^td zKIUCC35B|+MAIw+pf6KI+v&*{CS4z0p&1lnwSI_NE?#a))53jcT)x7W55N7Eiw%0 ztuf$;N74RN**A(dE4u2$M6z#pJ}hH zr@+u9w$qy`Bn*SSM2jVNC|(SLAsyHi#e+Z<94g(RV~*xs${dbi8}%7O00MeaBEWn7 z-S!%XY$S&}Vuh{MCL2x+|&ix!2{ZmkIqaI^7sy=?+@~!4{n8iqMEd4A>KX7 zb_M4}sL8 z5(*=ev)0}ez>w)Fbxja*DAeM_yB00j2=UY%O)BMbgJ}FQ_4=AcHt_OUVVlLb16K6>B39 z>rOO>lX3{K2N6Br2q)bQloh);1=x`uKtcJ#ckok`9uXLdE_z&Qee+nNZvG{DC-|O{Q?BPeFDeknLX040t7HTcK1Z9}J+Wd}nQ69M@eTi3*X7 zkXJHcXaWKfrOOptW1?n@5r7wIQ%b4}e(IFYZti=a7s#66izkYU*IrCkhUIfA5~R(p z^kyO?MtWAauji67KMoLMGCes?hfO2-JfJ8r8=ksUxj`HVcwr^ zKCF+TlFn2nBJ`pKv3!bD*CrQ{v`(rNBo#w;S8_Y9CXgz&ObBYHbctNd7+X`co_I3vv`fJ&yPB@mJ42kcO_s34wl*wRMWpqLhH? z0vN#=U78@aV=efx6K4yhhDQoeq!ZxZ3sL-Am#cLLZg{0sJlObW_+!)qsZKKZmUaa$ zC^1SefN_1-_Xtj&%EFQ^{9!Qpy)+y7#Uc7_z$T!YBjR!C!iXHm=7f)~U4N=Vlo1}3 z0S$n%06UAfm3eYxk|L}up_Qe_P$?{x!L2q!Pn z)#}Bfo+D~Mw0%!PMXaueHtaDBV63xLEKY-oIbsT>#k%q$-*lGkF|s03l?nV_`R=(5yIU?Wcx%AMJ$^ay zF2yOX{VB$Y`T_P5XrW6wRb)r@`EMnt00L8SOf)GgQXC76STUmj*wG!X4ZII78L#|3 z7`!9(GW`34J1&m9+m+1=rKiLT{LY;W!pZE)Q;JHKXCeh$PisG{kLvzyl`0C?rU>eQ zv)~k5U;G{Iz*@D_R^wPag_7wH6L&iCywW(FA;FzqJtruFHdn|~U6p_@@P6}uKwrgh z3bYG|o+8LTZo-t*eCAPXSx2!=mxq|AzMQod{wYq0(0SS-S(LKeU6ZSCK&EvLMm|EZ zzUSUx9<9mbhR%ew`*a-o%`BRUB?niwoJid~RPk30@TW`nq9k6zeezwR_LubQ4})2^ z1S}|R4VrOy7`XGmy+;1&DQ362`2iy+l~Ca@y(~@994sJKs^rd)MPQl`Au(hyuI_pT(2 zZL);v$|i1;5?Dy6Rlxy>`6g^DlMq68H1qss?_a>nc^-vxjQzc~{JM{*j; z028vd#|J#`5`zWcTjnVs9Ey8N`bQJHDy&K_(~d-{Um#KA|8Sbn$eM%0-;>^hl?tqZ zkrE5a*h3?q4Dy~12l!>7+?5hu0Zk`4f)piam5H)s!Y`?#;%u(e-lOcSE=rZxfIct3 zXEV{U+8~N}=1>|_5S04OjO=R**5vBYtdsW0((ucgS7`)>RD zJV&~jx;m5#NhQ)&qonJ8x9zZ9CcphfGr%0Skw>@+q6ciQ^y%+UQ1C)4VdTpK2L)3* zqph8IHtLxsVs$S$1rUzSc$8@6!TSSTxGV)@)0NTb$jl3N+P?%hQsWlP1MxE-K?Dwmr+O1X*9mj1!(a0qc1JS@!&XIxWxu*%g{-pRs(J-fae+c zC0zk?ikascO3^CKPtXjgB=#w56$U;T%B05>CIcmtF&Wd40jwHkvs9_bt5Guj7sx=L z-~oB;HVdI{=xmlg6pd#qm!k|)Ol5ku)pH`7BxqaE2JZ^egX@vg3s_ZxkFrjU!@-j| z0t)YuT}&lWAz^^*x@r3IX|Hoord%GelGqsylq8C9$?k1RuLOeZoy8>Uf{ zd8b)8VoeU}fCfJ2Fp8nV*D5%*dL)*UccZary3ND3jZZLn+jStv+(o|Hl>7bB`{13Y z1a>kPLm_^y~%PDd0QB~g5hCsKUP5m$;B z*C!x4D2gW_?j0PT9GoB3MX?XqW?Cd-QB+=q#m2&sp@-)F>0!I`Q@z!0oHU>Px{B)2 zUsr`FcFFv->(GC9H+Oc?Aq~}*yW$^gzeWP8q7o z5A#iKI1I;-gQ?9p$DbW37>$1KQ(G^V|J0U#W%+NbT#e^{u5MN~@8!R*@$)z5Z?-9@ zVa(kf7Yzdyr6Vdie{&p(ki;`K@N%FR`D)3p6nO2FLKR4LJV^ zXAwC%=o~d(v}&ziI;XX>R}Re^ruOWc9NCevG2B0B7>tb6?f%h)MHhQw4gRm#7uA3K zA%1mMRxT&rm@FZmZ-AV$F+!L0hYy9rl2aOi&km?>-xxDkD(d5#N zSvc9a@JCKNDhlcE^B3@E8~#SKO7dW!%}@${6ww^#M@5rV?=yOSD^A28f@XbDDQ?0n zIP^rl{jAvdCdX6CZ>X5sj^FqGDRSTBRB!nLP=UOj!lP#~I~v^`elmNEsyP_3q3<~R zhex%SxC$oH-{e%&Jp3-9C7(iJzsae&{JILzB)h@kE*;~Kld9uL_D#=8Zlu~!1*7V+ zsPh)wjf24@cbyfybw0xTH#xcP{2l@*L1%GaeDjTuj31VbJZI$xzc1bhn5OD3zY2@Q zGk+`g06Hk9Cj3j#uqUj4RI#L|C_?|b_78xIf1ugyuWKm)3~g1bEI=mLYzhsI*FLJR zhm-phYX*D$>o?!T3U{N~tfqB^dsl$Qg1_|r702m$LF)`XXgwL?jr|Adi;8qL*49ga!`A+h{_X#w53KZ`Uj8mS+!d4LEfhxN>iN8bp>+-$ zNA+h^h}W1GjlSu-dSGWI*X@Z?34uYVAEepc_kB?mx~=%btN=fkzx!iR{7yWFI%=rA z)ywd``6=ou@9=&CSjgYtj2#Ci_a{%wL2@mTC&kj|+)>>dCLMqoC`U3X=0d2;*tNvf z3g6_e{XwtmPGH(x1U;(GWQjzc_k8hxBmdv3*A9;BU;F*1vbj~M#@~Oox2yO3|JQl{ z;Sd2*ox&-?wHAt1b*7m*k`8(wD2W%$^g7Z-$*}bC*}siAZJoxFEz4BoV%yHikx3ax zdSov6=ggb2D+21A#sQhj;;04n#9tsQI~d4OnK6`&gpBWR>9}>+)6LQcQXFV45t%}e zjuxY%VN)lqC5Ss8O6>C}9bZ)i)J+s!R6k){T1s#jI{OF3*2%Gc33~01nrATfcBJ6O zw<6po990TN{P^I9W(0m2Atq8Wx?QQY=Cxw9WqiJuUd&PvjTF~mLuhEAPDZO3dALwY zSZalvB@x%eI;{RvMpIH-j)@-8RDiiVwiOtH1F9Qll-UqXu2@H#wnpXm|wA^?Xn70gSWWIgGZn$ zPfOW8D(_;`FG!n_a%MiQi&gLhz#z9(gP#T_rSOl^*$~_uw8=Uv=4wbg?WmnLx7IaY zYCh=q1&+aLn085yl+<8q1>SHr(4mz$PPcr3kwQD02`1;~hVL9{n`Kxd?KclfWY~5! zosM@mHmGhU!S-40=t$L~dN%OGrvIB*A@us

b;LI!% zQn8;OwQg7i7)VTu>ggDNWXD)3iP*(7?(zsOi8~pfbvLP;V# zmzNNuNU;9f*dlys=l2tBeJMRn{8smusX&}zDYdP`) zAPy*x4!>z-XcgrE+UwUd!}4RGWp*_xN>!mFk5Jp(v)MP>_L_kyQ@oTNC)#Q@Sm^PT zRA+_wHK+Gy3=~p`DLWAzzp5XdQZ82lDSVAV|JLCRMbuLddw40)Cwio_79;MHk@r27 z(Z_SRt+IoZeiic2fD#kk!hU(fDc2_EY@XtHV{(ge2aZQ0%OLV4{ZcyQ=<+ILWjMP) zi~0-gfgJ1K!TxvAc46#yLqn;Jr9}#1HseqPs-b2jr`i-AbNZTiSx2*XrBe>{#ASV(T}`I67OGlkzr8JjD^wYJ0@w0d|KP?Vwq!z2#=QJo0XJf#V(L!e z@)IJ(cXi$gjNTAXhCPNNX;5OgDpH6%X8+i{OPdxMCR1huV+&Q1M>FY|%n3yNp*t1! zs;r>I(yrnv>XI+Q#f@`Cm?b(;HhGJV(dDC1&}yEf-Gte?3HL1+fZ3!tcPVzEiOzfu)(T+uiI451G_Q4LVvF7(VC0_JDH8A5@&iWN7K=>&%4a6EaNJXqhI9aM@s-SEsa(^ zJ5H@{%#lJYP6Otvp~?fcL!?R1;Fiw-&ng%REq6)cx%5k-blZ4G8WhJ28bF>uutf6t z@xrN=)TBL6K>7qBjl3Kq=ndZ$4hi$l^TzUthhnx+PO0gv-zVD%3CNPmf~!6V*zpT9 zWuoqZ{9cP##eMfyO#Ku1NN+)AU#E!vodocF)vh6nT8jA z3|u91bw`l1`Mu3m8gD_zQ4&O_kO&^U^vnD3P_bir1OuIo0*mXIQU@YyI5dq5>9NK0v ziE@~C)meIxCy-c7Dw&i=x6@Ni41C$2e;=96>ov>TZrlb+kqGpqL1h$q9m^i z5GZ4bIj`u*XCotwCE(+qf&m~lXMj&;FwhSG$+IZTf^+}=b9QoY@+bKJh@H*2{a0nP zx^w^j^EG}j8u%KgAl69;M~qCh6ad_?2kZcmPsNCYGq`u`^iyy!2P?WEQg}^{NkOL0 zKouubAZ1W*C{?;_pW7XCt_!Sm5GZv)6db?^#fdxvw7!&SHM$gp75&S*;~upqWiS3k zxgP=yS+4S$;9A~EZbG}ihDa4$ZAVRf6NZ6N=F!MvMKiI2NT^(osC5JOz8C=8q=`Gq z+CmGAr6)l6qp<68p+v0SAyY{{vE#AiO>j)W(`y_IcI1EHznrgo|55wB;^Wy)<^YA|iow4)Z+}wP8kN>}l{qF-l_A4?iaxc1s zMnN7!t&39F$gGmcKvv+G@G~=TO2Rg^J2GP@^j3zS%0+qe$wj52xKiD2gz>#}-E`kR zblg*JaWpbjW91T7sg!v>YM}4F+xqU_cIlJuKgX`-nChSN{?EhzJ3DdzZy*@=_CH_w z{gs&Qoe{SODt z$uhrJ|KT_)k|7)WbO7u`E-(J&tWf%8vHDGg9xzsjLCCWS^J-ltu3L3hB>3#@(XSO< zg6mT>J(MUZTRLuF#&1G4*N~OcIsWbtM^-F;>G1-LCV|ag;s&>T8M? ztFG0qSaqTme?$8i)otNU>#PQ`y11pz7rXz`zW=lHfOp{kcDBp+{NLBc|LXj$*RoRg zOUwV;aNKeH5Abr2|G&o1#=4bjvWxlZzS}Nh@G$jY#VNpqs0{|9MTr?ii}F&Vt)*Cp z|K~7gtWP~T{RJO?tt@e3eZz77rcBMBhSQ!Ol&+o|MIiG+sa@7ZV+OnE(whe3sa=LP zlB3JeF65A?_!ei^y$LrsPDP>^jgY))vfK~4(}7*=O(r9nzat%O*&TXC210!ERy;#0 z_Ajw&zA3L3bhNgPJGrFSjDl#MA01%=vyX+Sf#!qfHL0p5sB~Gy=h#G*O|HRzlvQb2 zd~`nUIZpS=ovf_mqZ_L9p#Y;OIx{p8$lWR#X?fTg= z{rysJt7^pktZ@DWQ2}1!qwoeHId){s`0#LE7I$Ib!gujjJ-9s^k@p5iXz_K{W^DS`S4banIX+w10!HQ?OaqZ)kidURqH%V(-}*uuu}K?Y&P{*+h~S(tEtu8* z;md>CSq-Lz2tr-(_^gt1vTh5tK~Tr5Dk0dop}`DD_iAm1S)Z7u0$)WYsD4QF@K=XE zHng6MQ_`u=t9)H@IKvX)wQm2C&oiW66rs+G?}^l*aEbJzklu)2S|Y+7#@op?(F)5< zf$#Nc|0(jHKK3sz|5eL7<*lUrcOU=bze)Z}k@d8cHD5}E0yL#tEE0}93|}(c@JCCD zin6%>r3FZe_$%c|zYpTxir?E)<#&?N3<(V%N!}F4Zv}@#U(``B974#;pG(1%UNFOrEx6Wj2zwQuG1JNjUhp619pX z@>L4GxLQ~NirzT{j=kQ2k}Al_fAjl2uP>tVvle~Qjm}zDGx-@?vdg@zw;Au8h4593 z@@Rd+0{$c)xU8@Bvsd+2qrsB;-(kpcP*8Fmw05R<(Oky_su6uedd3jh*Gm9(*y4<|WQ5;Rrm;xXYYiqG-C9ZH`- zLIOf>`?S8_s2z2hC(ZhvRZl$+Lsv)k7dqHy#?_OJmB855vZ5^}j#ohze6Cn;B?)#7 zA#iQH2C{V4TroO-t@X>Euw?+LAIjmXnOQHAIEvvi0Jf^6KY_2$#imq!MDoN(b$hTe zH`)_Ew8DPiHwBJrvVKwa9L>4By8<-%6wP+gxc-3gDJDpgnI3?a0zl#w9N*;RdGnnk zJ%#@^CfF!(7<%Q4bcXw#=#Y;&i6yK~ac8h13Oq@HD|x2owSjhYaaebwCm6}7IK!rd zk|tXm6vYXN{;&}|O9ofe!AvL9U^Y zVVek}r3}Eo_0H65FKdk^5JSh(8nB90i_dh#5-(6wIz74@_4?0^_StSa9oyB)0v*g+ z1~F!_AGmacQ^x>O8cjhMkASOeG|$`h%u$;51<272$m_x2@IXXL3{{Y@odo-Q$}CP> zCub+kllJ-P=}9Yl!Hp3h5x-|f-_Cs-=2HewLqHij&^$S)|CGJ@fWt&c{#Fkcv9W}0 zB6OTKLjCOEhVjNJii}Jd z8X56MI)=FbDpQv3W?`%}WpfI`Qr&%w2^oqlW0~g9CB;=DQMGR~A$H*99KDpc~2Ld3e+|)TipR1EqH4kj?j2uM^%*}7VoDR7-(j<+Af^#eK?8!s9Cu$|SaO1&B!@G9H1lrHOMZ;)n?>jkjwGR<&nGO+0K^HnIqf9< z&LnJiqim_9Esf!i$k{FFS!@*ZRAVD(0yBREJG}?pk2xdFS(iZvZb1mr-ihJ@pZSDg zkb}P#Er>9>@s9N18AzciLg-S0_k7VkOTesbu{Tt3RjxPon{OINA4uYGsP^1yj?C-aT*1Zwqma7Z&3X z@v`b$<_F^Cn<;g-GU{%>jds4Q;q$)|bt2?6PtIyT)f)fN7<37fLO;`(PvbUH>f5L- zp=xBwYotUkeOEBt7OY{@l)Ur{K!uh6Gz#{`4*>eE`ES*H{703yBwQq(hqx(Y&b)09 znm!*^W5ASlKHroQs*$_Q>htcB&7R+SK16n5M%$lnMsZ4>oReb!SY$5y(fP~T|BT!L zqW4cV0a_6MyIfA>f8E}?_y7B^vj0i5;#tln=&xz(^EC{6A_Jb>mG>b}9@X?)!d554 z1}9-}qZ}x3c4+7eybnLC_I&o7VC}Pi=_9*}DV?riaQrCAX^y`=ecvg;(vS6$tCYnfRiQ{N3}kem838Z-#l4dC;!fvhJh&gRxkUOCe5P&AtsdV~ zpWb8q8$}zCM7xT6BzKe71;6C5KrKLhd@d^0Idg1cr%>;5dd1mc13E~NqjokAo&La} z7!EYFLXJZYOfc_<9|)*vHe`XJ*%0-RY&H4UA{mC08T%t@Qc$K;0x$+&#jv!*tH_EL z>?O>>AZ6o+UTucn5NkZlX}GKw>+kcmh|^@>o7r(+9wdjcUCfpzUy zKpO)8c=SwExjt?W?ZdikowKe&Uc`|bc1DZj22TOOY(;222q~1K6r}0aKYl;Gfrx1X9Ro>@O<*D2G7t)($PAN-Eb?@Bw-{k*CLDoKl@81&o zze?rtwkOvmp@l0_<212xO2WtNwwev(??8hRwi>4gZ~{mxm(AckqS^` zVOaagxpg|JWtoamtBc!cNfmXc5$3QhaJ^cb^auS{(pm7y90q*SD@~@IOOQRT-J3n? z?+iNkrgQq6F6^%tPP5o~ThplYgi9+bld4Inaa>wWX-f}Vd6So;^~YRwO`1VW|7{-1hu7isQT}wM*j-R*-2dgqLE}$ zBeRq)7L_j;cWCmZHL-KlH}$jgW~*M?f0gYd#>h>fK&2+dG%FL&1>nSFR+(DT$vhqD zSJYYl$MH=|b4WISQ%%#3&f^6B%^0B4t?2s_Tu$qsZS;frA^sk{? z&X~(z(e&~DCqw_+rX;K3XNv=W`}psh)$RNIKY#l9!{3wc`%ixaSP=ic^7wK5{I|=S z_wnDq%FleO+;kmyhQ>Tg!JefukD}l$L7dZAcI5iznk69D4Zx=?C`qSzcdk$}8|Z4K zxWQeqnqeGJnqwPKiW@#y{;*vxm-AKyX;xKv45d`8@o(hwL`mIM#g}2GsZN4A$*V7gK;Xv(8*DeXDbMdOrJeL zivKLNL<=XU29gu}NW2`elBQ$5V zHq+{DCF^ZdJq8IIQs~swB7dE}1eX6-;FmeVg^*ma$#Jc$z^+7(`3vwr=6d{O0UZDG zYx5Bm^`B0aEUSvprb^WxSy>HmKX{Z|YC09=v*V5*Iuh!L86%aYnH6Lgqys=E{2b zRhSn`RwOYLGX~&;`^ixUN2;IU@12ACi}RP9UaTOtmXrone;FgE@J*+4`KF`!j8irL zmy_{RIVS{+J8(>&m0?ozy&KEauAT0RlT!+l_5uE%C_lC&PKSQscy+qPk+%7ie1gn9 zsAetOuyqg4D+&-B=V?Ndr_so7d7ef!Q9O+@*XA6CA#f-f8*Ww&&Ajo@zggMiWERqt z&1!_t{LrYgh6Vt|qKw%q^CTu}M!l=8YSxbHWNMG8Rd#WMC4h&xTQ1&)1)QWl zaCris&Pk^6f0$+dxc>Qgj0ODP*3MQu{!?{l^Pd0vDnDmefXK*m3(*wt520|ydv9{X z><9V_PlDcz-I%9=m|l4tFc3uqOg8P}7Y9BbAy-%u;?VO3Abxrjh#m0EwL1ZxDHvkq zP~<%6)(u25oLydWz5^fvJ|%q3JJ9HI;$8mGW#_XJv@AK!84TMG27}<*A6)`_WyTJr*@i-Xu&^bW3{5@v7$z7UNas93stMorI z2&6kQLr|hG9-sm|0bx)4I+zW5;=y(5|RYugb!SasurN zN_1AD%^tgxso$Lq;BG`~f(=nIA4G44K6b=0(7!ig7Rn8e4Gu&FfI-f;i0-K`_Pq)E}iJ3ZX++sE8i}IYwswn&V z5F;>w!DX<5cQ6WeWCH`Oq8E6fgEpCz`zCqFK$5L9ZqUL3@AMFW#*^T^-}7MBWMWsu zWXNL={)6nk5%?7yGqE>We-c7Zq7n1@cX-7N!GTP%v?s2DYwtZ~E1(SvMs(t1=o$y{ zX*%v8BqWeLI=ZEJWdLMsgfg`*FYe52>JQ+?df~3)#IlWYCuo8Rdtq*X48h^XE*dP) z=tD;=T(X51c=~|9N=H`z6j7o+M5Na+Ux9l#flZ{gE`0#>g^K z)0XFJK*n~2>$T;DaOAJz+8+$)SrU;Aj5F|*s+Xw?Tr{A0h(`K?`x2AcXoNFD$_-O= zLPRb@w|nJ}Bz^&q46R4oY971mApj120t-)L7fk};7l&p-8|_N0>(Fx{{uj!^(0}j2 zArAwf%)x}u1V2qDE{4}pb8@Fsm=EkGZk0q%C5IG`_}{Fa@Y7N~;n__1?50-}>7-6< zg3b-Ypg-{jh!&=lk*s7RB^#3s000vhJ}gD(BD*?$=BnA16mua19(`fea2o%A?7s7G zpS}|RFSfSh@gFufAK&MH{whEFhex%SZ4lmzCsk2=4Vc+EKWiLeiAB$1*gsBig@%5| zfj)M{H#zDi?>NAw04e(>w|{z?7sX@v(rE4%8h&qawj8OP}kJa+_@Cqq%} z>n@;HK)3^My+myiD>}|_f(}T?;ZkGOR(DBg(V7tHK771hs%TIAO0I#wQnEyM&4WfuRTz2ydHxEi@m~Pbmf(-CbpI>cmF@Wb-@2Fozta29gAEXjfJt-y=KKw> zl{}OeB;C!%8<>00q^T%5{mp^8?O-;+Oy9E+D+dPt#RNGnrzAGKX?J7NE%g|bdK;=z z=%}yZO~|-qLy07b4=@=VXP@$l6OoRlK>YN$BtgszI?g>KhzB&hv|;D0`d&qo0k@qd-a z3H<-Ka&Q0rRes`^{TYbI$$PCzBXsy|6gUwIdge{9%8o`q&q$Hz#POnP!&vEA`QH2U zuX+Dv47acK{v#e&EAjWA$2;Zw`~Nk5T3*i&*{lSaI8;8(LJATTGJl69z=oiD4%KC0 zL0tROD^ynFzaa5B!=UH){Vu823Z!ZoqxNWu+Bm6&?lJ#{s*YgdU;3zVCE5yXoWla# z;6`Zs7E+VGoOqYw6euxGAr^~JI86_R_a@XQIqL^~qsa*77i%(fZ!p@C(!x3*9tM+; z)b22YVK60~IX-n^Xt;_0-s_PSB|jI1L4SIUYm=)M4r%;R0R?Od?#2XHJmR&7A?!to zHNd(hYlC?^E^g+oZ?)DIjrOW=T+;mUi0YCc z7m%XkuwL*Ps{~Ow=$yRxdwu_`O_lNet`xAUZ{?dDc9N$j4D4lBbyo_+H#ylXPb$Fu zyeLB94^|BxDsR?x)I@gml;(F9RY~j3)+?@4J({yv|3Ak;0yZ0XAxM098E{?g*8XYj z?A5bxa^aN+>mOhD@>qD#Xz8*GH}r_`e3O&a^Lgi>(LOtD9MzvuA?glG)63s8)s)}l zR0CL&gOqqzVEvULTtR`ttOI}U3f0_M$#r|8R6>QMMxF@2-S;3O3q7d#!>j;5m%saC zQT$FkH;1%(8NN3^MP23Z1AqS)@&APXzq0+;=5{q9{{sVXkN>~MPh`RJQ@!>|~X94W!56x_U&E zfhJx_w1WalICPL*m}P%9c%V&`ybmsgWkY!hjg%aamvC;OXa?_*p0R<1$FKS+>*BQ1 z@IUtw->s);5(RrAuE-AoXFd%sJ(kG=oCijt#9x70jzKI6&?16lN1$c!X&BO94ijB6 z`{Ji>=yB8=;Qn5tF$Yk>5es7NsXGPeBW&e3zreIm)y@dIt&%YuoU7uJq=g3a9GdMB zAxdO7Vhq2dozy_vN|IGqh?AUnT@M6HvZV;8J&@{38mwp?vMaq9m&D|7DuwGCW6fj- zL1vf^FzXm9Q$NM1Zlt&g%Tt?$FCY3d9R|tI0UDM`GY^D|E6*I4hP_5pOEs?&gVi;N z)WL{>%8@vMq26qbkWUsn(em+7q(O(*D~TF@b^tiM(*9Vt6B}Pj)sc<>Obsi>Vh*#hNjXwUX{JoT4$!r8feJ8|pb%GnB%I z!3==}){iFE1%O6cINL8FK+^@37mH8OoseDJZ$Lzx3$Ks25}QcVBGz||J!#sNqiox* zGPgwoEiA@sb<*CbIvPsxSemc5N)@c^3Wm`FA_-Tl_58^i z6Duy&IzDd8*hlNh{n=y!okP!hNNs=FqZt950*ZlIhW-UY-Nj6r0@2i@Q88K`@g~9K ze+mZgU^kA?>Jnhxc{-54{Q&zsD_2UF*S*V9&wKuF&i^R^ulsfQzwJsQ{?AsmT)F4} zzQ)hSI*EW}cs3i8Bbt232YHh3+&~!5_gLA;7qd_KVzvsDH3n0}0CGQ=+_>+=Q?EF5 z{lTuNm8jr{@T$~(4+O9K`}6c(b_ybP!$jr{09?SwVXscZbDLkv^D@G zlHU4;I)XxS8z9_+wvU<&zHFY0mvS3UXBPv%D~|jwAPo<(&lpR>D^loEN7&>LXVF$# z-$S(eBuu|2q{-3~uFLBNwWE`-EIosT) zqaq_;nNEmW{1TC7vZt54MUR;0@y+7%qh4If*&rFAXfO9LY%Y+Bf{=FFLGom&eRR64 zxi5&F$J^o<=&Pu`hXdVrhZhsScL~29*F?Em+5D~`&f7Iu#QH`eW6@In)T;_TU#-f# zIplXr&TyRS1~oWh9T@;h3qZmCDU`pNRfj&WW`%~Jz!0(Q2ZoPa+Lub^mulvh&CD-b znP0Zw!UqoOoLIfg<`drlk4%SBm;Yn{YsHVL9U?xA_jZanl0xsL^|uAx(Z|&OLS(Y7 z4pZaJlfy1~Y$w-7&7?bHdd^dOO1tD88wU~k7E3L>L|fVqJ%iAkfeJ=wuG$zd0f+G! zu{cza6G`bsu0M93DLbTkN*t=OhQv9>7b!bQIZE>+mp(mJojR3)X3S2}%>8m?Zxsk` z)93<+lP+~CQ>)NNC@V+@QCTf-r&_@NI^I8l#f}c3VjzVobtyxd$($olVN^|Y`|MfS z>NyO7vi5nx9B1HS)=xn<7>&T^SOH@6X6LQSj6u%F+)0jFu6|qn5c_|QPV+D~0<4oS z2>hj@eyP6A>#v)ta7+EN{WcF0&4XuRC-1Bn`NoPB>CMjm&#)%pKi%Qz=3G(c+JVW9 z;Gbm3x5Nf`)A;%^$;6bBP4Et2I0I{;gmZ+ff*#ftdzNKuSe)}m@=)Z2-53u5NEL1U zvwxKf`u{%eS(Pp(f!pi4;Z)W9aClhA`VX|FRbWGJGU+fqdV|(F$F-k3^;YYo^{Ddp z+3F||P}h zr%Ge%w-d&A;h#YoTmLj+Z2c2tu~>fE)MT``O9#6k*=)Z<4<$=vt(}`!*6+tEqlasH z&2d`kv^!3pHthT~=mvu@k&!nZB5djpy@ivoL{`Z&%j7lqu;p=^<*l&&iN^2Y}Z zQbrg~RBzX~`qq-wPk*NB+mvQ30IY|eeJauiOh2trbDzej(3HLz1XF$~>;>JBeRJU^ z=h~-@vwUjv)6>=ocR-WGhtB~TlcM$IAP9Q+kO4SyLaeNKgR_!~O0W0U%;shQl;CVc z;oNv`8O@~G>)dE-EV%JIrPtx04YsO6iUTP1aE{P~qz`f;{sSGFeZdT*I6=J@M6%cX zo=zi;-OIN>ipVC5l@!3AIB}-c2HjOU6OaqNaB8(=c@*STp3Wpk5=^XmB@$gR;G9TA zoTJ20Z?*Ur_Ke*IhTxz0U!bi6Aodd(JWj03AQ;cYD*6(vCL_}c+Ak?e;+>O!+B*ar z^k%F4-Hr^dD|esb&kkY=|(CEZKb(FKujV<3Ltw4#5ph* zI1CNKYE7K8@sDQ$Cf<=7pmX)wYimbqyUoJFw1sV|g~@nvu?r5sDP-SjrA*f<-t)E5wx*)RkipB1FQt0W0bT8u61QKBM4(7$PqU2gu7N zlqf4BBE!J_M8LD3$PfvFC6c-_)Sb8ffHu|N`6|Q}#=kmFZd*1oo5;jwh za7#_rYRccrhO#iC6JjBuF!gT0t6eLkeUS^V}O1(s-p01>oqTH@zWK5RhGEpyanKejMnVABk zP(|gmx?uj&s;B%!6LpD;jWo7dlS4+uo?0($YQ4;93E2A53hw0EaYHL;b9Dsr4NzN<=&sv{#t`H_Hz z0qLR(Ltta3U&nNpl36g+!MbI&gpXpxUifciw0s>xe6*?v*aJTVzVRm4K05#bzJo74 z&6B+BtluBZ!Yla-z!IR7BiY+1}hqQW+O$%q4J^XeCHCQ)4(Sii;#oNW}>{J|U2-D@#Pm z;i|$ou^=j~6WNLk=1pB-^eS$M{-&FTqZCK76Gun;V&L9jJg?Utn~C9(vowe8IG&Lo zA_L1NMBK0qg44zU{6`tO1&FvQOaZmSUN{EbGynz?P2=#gQHZD+M|z_=6!i%295qAW zlviv$7ZWDe^W!KLvxaU%Dp;j8Vgg(hA~XVWcMONU>)5+PQ*AU>3-fPkR%T@r&Db1M#Joirl<(8?{@1?$ux)eqYrOyLY;8V% zoXG$1_&)x_SA74G$9?|*bpHT!{{VFV0QA`(fSz_Krg7$*ka`t3I6pqE9UTGV-6jSV zP?7rN_boRR_6&i`19jI(@VkFlx_?;uw|`httAMqm{{CdY(>^*m>$K|sb6#(sp@4@Q zQmN#vn$c(D2WnQ~$F6x$Pw5rYt-?=UgElaQN_*V7@?0dt0OFm_tg?eP?kK*{&zwzw z%1=mzgWX_Q;$

7&Ph(g6pL!Pu=j{($k=xuYjXjrn2^ZeD) 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

dqP4u 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 literal 0 HcmV?d00001 diff --git a/Changes b/Changes index 823a054..ac367b8 100644 --- a/Changes +++ b/Changes @@ -1,6 +1,14 @@ I only began this file with ncpfs-0.12. If you're interested in older versions, you can find them on ftp.gwdg.de:/pub/linux/misc/ncpfs/old. +ncpfs-2.0.6 -> ncpfs-2.0.7 +- Hopefully removed one security problem in ncpumount. +- Added command line flag to pserver.c +- Heavily reconstructed ncpfs utils. Created the lib/ dir. +- Separated the uid utils in sutil +- Add nwsfind to enable users to use ncpfs safely without setting + the utils setuid root. + ncpfs-2.0.5 -> ncpfs-2.0.6 - Added a short description of a problem that I need help with to the file BUGS. If you know a bit of the linux networking code, please diff --git a/FAQ b/FAQ index 904c800..8a3d947 100644 --- a/FAQ +++ b/FAQ @@ -1,5 +1,5 @@ There is certainly not enough material to call this an FAQ, but some -questions reach me regularly. Probably the documenation is not clear +questions reach me regularly. Probably the documentation is not clear enough. ------------------------------------------------------------------------------- diff --git a/Makefile b/Makefile index ab8fba4..3f6f699 100644 --- a/Makefile +++ b/Makefile @@ -2,7 +2,7 @@ # Makefile for the linux ncp-filesystem routines. # -VERSION = 2.0.6 +VERSION = 2.0.7 # If you are using kerneld to autoload ncp support, # uncomment this (kerneld is in linux since about 1.3.57): @@ -11,33 +11,39 @@ VERSION = 2.0.6 # If your system is ELF, either also do a 'make install', or append the util/ # directory where the dynamic library resides to the environment # variable LD_LIBRARY_PATH -HAVE_ELF=$(shell file `which gcc`|grep ELF >/dev/null && echo -n yes ) - +HAVE_ELF=$(shell file `whereis gcc|cut -d ' ' -f 2`| \ + grep ELF >/dev/null && echo -n yes ) TOPDIR = $(shell pwd) -BINDIR = /usr/local/bin +BINDIR = /usr/bin SBINDIR = /sbin -INTERM_BINDIR = $(TOPDIR)/bin -SUBDIRS = util ipx-1.0 man +SUBDIRS = lib sutil util ipx-1.0 man KVERSION=$(shell uname -r | cut -b1-3) +INCLUDES=-I$(TOPDIR)/include + ifeq ($(KVERSION),1.2) SUBDIRS += kernel-1.2/src -INCLUDES = -I$(TOPDIR)/kernel-1.2 +INCLUDES += -I$(TOPDIR)/kernel-1.2 endif -export INCLUDES BINDIR INTERM_BINDIR SBINDIR KERNELD VERSION HAVE_ELF +CFLAGS = -Wall $(INCLUDES) $(KERNELD) -DNCPFS_VERSION=\"$(VERSION)\" + +#CFLAGS += -g +CFLAGS += -O2 + +export INCLUDES BINDIR SBINDIR KERNELD VERSION HAVE_ELF CFLAGS all: for i in $(SUBDIRS); do make -C $$i all; done @if [ "$(HAVE_ELF)" = yes ] ;\ then \ echo ; echo ; echo ;\ - echo Please add \'`pwd`/util\' to the environment ; \ + echo Please add \'`pwd`/lib\' to the environment ; \ echo variable LD_LIBRARY_PATH by executing ; \ echo ;\ - echo export LD_LIBRARY_PATH=\"\$$LD_LIBRARY_PATH:`pwd`/util\" ; \ + echo export LD_LIBRARY_PATH=\"\$$LD_LIBRARY_PATH:`pwd`/lib\" ; \ echo ;\ echo or do a \'make install\'. ;\ echo ;\ @@ -49,17 +55,16 @@ dep: install: for i in $(SUBDIRS); do make -C $$i install; done -clean: - rm -f `find . -type f -name '*.o' -print` - rm -f `find . -type f -name '*~' -print` - rm -f `find . -type f -name '.depend' -print` - rm -f `find . -type f -name '*.out' -print` +clean_me: + rm -f `find -name '*.out'` + rm -f `find -name '*~'` + rm -f ncpfs.tgz + +clean: clean_me for i in $(SUBDIRS); do make -C $$i clean; done -mrproper: clean - rm -fr $(INTERM_BINDIR)/* ncpfs.tgz - make -C util mrproper - make -C ipxdump mrproper +mrproper: clean_me + for i in $(SUBDIRS) ipxdump; do make -C $$i mrproper; done modules: ncpfs.o diff --git a/TODO b/TODO index d3663bf..b5e4d5c 100644 --- a/TODO +++ b/TODO @@ -1,14 +1,11 @@ Here's a list of things I want to do. Feel free to send suggestions, or even help me ;-). -- Add flags to pserver's command line, so that the print command can - find out the name of user who printed the job. - - do rtt estimation, like tcp does. - Do better connection management. I imagine to create a ncpd. -- When ncp is done, one can think about mounting several volumes over +- When ncpd is done, one can think about mounting several volumes over a single NCP connection. This should make the trade-off mentioned in ncpmount.8 unnecessary. diff --git a/util/nwbpsecurity b/bin/nwbpsecurity similarity index 100% rename from util/nwbpsecurity rename to bin/nwbpsecurity diff --git a/util/start_ipx b/bin/start_ipx similarity index 100% rename from util/start_ipx rename to bin/start_ipx diff --git a/util/com_err/com_err.h b/include/com_err.h similarity index 100% rename from util/com_err/com_err.h rename to include/com_err.h diff --git a/util/ipxlib.h b/include/ipxlib.h similarity index 100% rename from util/ipxlib.h rename to include/ipxlib.h diff --git a/util/ncplib.h b/include/ncplib.h similarity index 99% rename from util/ncplib.h rename to include/ncplib.h index 0179b24..3fc078e 100644 --- a/util/ncplib.h +++ b/include/ncplib.h @@ -121,6 +121,10 @@ ncp_find_permanent(const struct ncp_conn_spec *spec); struct sockaddr_ipx * ncp_find_fileserver(const char *server_name, long *err); +/* Find the address of a server */ +struct sockaddr_ipx * +ncp_find_server(const char **server_name, int type, long *err); + /* Detach from a permanent connection or destroy a temporary connection */ long diff --git a/ipx-1.0/Gregs.Makefile b/ipx-1.0/Gregs.Makefile deleted file mode 100644 index ca4e086..0000000 --- a/ipx-1.0/Gregs.Makefile +++ /dev/null @@ -1,24 +0,0 @@ -CFLAGS = -O2 -Wall -UTILS = ipx_configure ipx_interface ipx_internal_net ipx_route -all: $(UTILS) - -clean: - rm -f $(UTILS) *.o rip sap ipxrcv ipxsend - -install: $(UTILS) - for i in $(UTILS); \ - do \ - install --strip $$i /sbin; \ - install $$i.8 /usr/man/man8; \ - done - install init.ipx /etc/rc.d/init.d/ipx - install -m 0644 config.ipx /etc/sysconfig/ipx - rm -f /etc/rc.d/rc2.d/S15ipx - ln -sf /etc/rc.d/init.d/ipx /etc/rc.d/rc2.d/S15ipx - rm -f /etc/rc.d/rc3.d/S15ipx - ln -sf /etc/rc.d/init.d/ipx /etc/rc.d/rc3.d/S15ipx - rm -f /etc/rc.d/rc5.d/S15ipx - ln -sf /etc/rc.d/init.d/ipx /etc/rc.d/rc5.d/S15ipx - rm -f /etc/rc.d/rc6.d/K55ipx - ln -sf /etc/rc.d/init.d/ipx /etc/rc.d/rc6.d/K55ipx - diff --git a/ipx-1.0/Makefile b/ipx-1.0/Makefile index 47b4a18..c12bf8d 100644 --- a/ipx-1.0/Makefile +++ b/ipx-1.0/Makefile @@ -1,30 +1,19 @@ CFLAGS = -O2 -Wall -UTILS = $(INTERM_BINDIR)/ipx_configure $(INTERM_BINDIR)/ipx_interface \ - $(INTERM_BINDIR)/ipx_internal_net $(INTERM_BINDIR)/ipx_route +UTILS = ipx_configure ipx_interface ipx_internal_net ipx_route all: $(UTILS) -$(INTERM_BINDIR)/ipx_configure: ipx_configure.o - $(CC) -o $(INTERM_BINDIR)/ipx_configure ipx_configure.o - -$(INTERM_BINDIR)/ipx_interface: ipx_interface.o - $(CC) -o $(INTERM_BINDIR)/ipx_interface ipx_interface.o - -$(INTERM_BINDIR)/ipx_internal_net: ipx_internal_net.o - $(CC) -o $(INTERM_BINDIR)/ipx_internal_net ipx_internal_net.o - -$(INTERM_BINDIR)/ipx_route: ipx_route.o - $(CC) -o $(INTERM_BINDIR)/ipx_route ipx_route.o - dep: $(CPP) -M $(INCLUDES) *.c > .depend clean: rm -f $(UTILS) *.o rip sap ipxrcv ipxsend +mrproper: clean + rm -f .depend + install: $(UTILS) for i in $(UTILS); \ do \ install $$i $(BINDIR); \ done - diff --git a/lib/Makefile b/lib/Makefile new file mode 100644 index 0000000..fa86697 --- /dev/null +++ b/lib/Makefile @@ -0,0 +1,76 @@ +# +# Makefile for the linux ncp-filesystem routines. +# + +CC = gcc + +ifeq ($(HAVE_ELF),yes) +PIC_FLAG = -fPIC +NCP_LIB = libncp.so.1.0 +LIB_LINK_COMMAND = gcc -shared -Wl,-soname,libncp.so.1 -o $(NCP_LIB) +INSTALL_LIB = install $(NCP_LIB) -m 755 /lib; \ + ln -sf $(NCP_LIB) /lib/libncp.so.1; \ + ldconfig +export PIC_FLAG +else +NCP_LIB = libncp.a +LIB_LINK_COMMAND = ar r libncp.a +endif + +CFLAGS += $(PIC_FLAG) + +default: + make -C .. + +all: libcom_err.a ncplib_err.o $(NCP_LIB) + +install: + $(INSTALL_LIB) + +ncplib.o: ncplib.c ncplib_err.h + $(CC) $(CFLAGS) -finline-functions -c ncplib.c + +COM_ERR_CFILES = com_err/com_err.c com_err/error_message.c com_err/et_name.c \ + com_err/init_et.c +COM_ERR_OFILES = com_err/com_err.o com_err/error_message.o com_err/et_name.o \ + com_err/init_et.o + +libcom_err.a: $(COM_ERR_CFILES) + make -C com_err + +$(NCP_LIB): ncplib.o ncplib_err.o libcom_err.a + $(LIB_LINK_COMMAND) ncplib.o ncplib_err.o $(COM_ERR_OFILES) + ln -sf libncp.so.1.0 libncp.so.1 + ln -sf libncp.so.1 libncp.so + export LD_LIBRARY_PATH=`pwd`:LD_LIBRARY_PATH + +ncplib_err.o: ncplib_err.h ncplib_err.c + $(CC) $(CFLAGS) -c ncplib_err.c + +ncplib_err.h: ncplib_err.et + com_err/compile_et ncplib_err + ln -sf ../lib/ncplib_err.h ../include/ncplib_err.h + +ncplib_err.c: ncplib_err.et + com_err/compile_et ncplib_err + +dep: ncplib_err.h + make -C com_err dep + $(CPP) -M $(INCLUDES) *.c > .depend + +clean: + make -C com_err clean + rm -f *.o *~ ncplib_err.[ch] ../include/ncplib_err.h + rm -f libncp.* + +mrproper: clean + make -C com_err mrproper + rm -f $(UTILS) .depend $(DISTFILE) + +# +# include a dependency file if one exists +# +ifeq (.depend,$(wildcard .depend)) +include .depend +endif + diff --git a/util/com_err/ChangeLog b/lib/com_err/ChangeLog similarity index 100% rename from util/com_err/ChangeLog rename to lib/com_err/ChangeLog diff --git a/util/com_err/Makefile b/lib/com_err/Makefile similarity index 74% rename from util/com_err/Makefile rename to lib/com_err/Makefile index 271ce59..eeafb15 100644 --- a/util/com_err/Makefile +++ b/lib/com_err/Makefile @@ -5,13 +5,16 @@ OBJECTS = com_err.o error_message.o et_name.o init_et.o CFLAGS = -Wall -O2 $(PIC_FLAG) -all: $(OBJECTS) +all: ../libcom_err.a + +../libcom_err.a: $(OBJECTS) + ar r ../libcom_err.a $(OBJECTS) dep: $(CPP) -M $(INCLUDES) *.c > .depend clean: - rm -f *.o + rm -f *.o ../libcom_err.a mrproper: clean rm -f .depend diff --git a/util/com_err/com_err.3 b/lib/com_err/com_err.3 similarity index 100% rename from util/com_err/com_err.3 rename to lib/com_err/com_err.3 diff --git a/util/com_err/com_err.c b/lib/com_err/com_err.c similarity index 100% rename from util/com_err/com_err.c rename to lib/com_err/com_err.c diff --git a/lib/com_err/com_err.h b/lib/com_err/com_err.h new file mode 100644 index 0000000..f28dce8 --- /dev/null +++ b/lib/com_err/com_err.h @@ -0,0 +1,40 @@ +/* + * Header file for common error description library. + * + * Copyright 1988, Student Information Processing Board of the + * Massachusetts Institute of Technology. + * + * For copyright and distribution info, see the documentation supplied + * with this package. + */ + +#ifndef __COM_ERR_H + +typedef long errcode_t; + +#ifdef __STDC__ +#include + +/* ANSI C -- use prototypes etc */ +void com_err (const char *, long, const char *, ...); +void com_err_va (const char *whoami, errcode_t code, const char *fmt, + va_list args); +char const *error_message (long); +extern void (*com_err_hook) (const char *, long, const char *, va_list); +void (*set_com_err_hook (void (*) (const char *, long, const char *, va_list))) + (const char *, long, const char *, va_list); +void (*reset_com_err_hook (void)) (const char *, long, const char *, va_list); +int init_error_table(const char * const *msgs, int base, int count); +#else +/* no prototypes */ +void com_err (); +void com_err_va (); +char *error_message (); +extern void (*com_err_hook) (); +void (*set_com_err_hook ()) (); +void (*reset_com_err_hook ()) (); +int init_error_table(); +#endif + +#define __COM_ERR_H +#endif /* ! defined(__COM_ERR_H) */ diff --git a/util/com_err/com_err.texinfo b/lib/com_err/com_err.texinfo similarity index 100% rename from util/com_err/com_err.texinfo rename to lib/com_err/com_err.texinfo diff --git a/util/com_err/compile_et b/lib/com_err/compile_et similarity index 100% rename from util/com_err/compile_et rename to lib/com_err/compile_et diff --git a/util/com_err/compile_et.1 b/lib/com_err/compile_et.1 similarity index 100% rename from util/com_err/compile_et.1 rename to lib/com_err/compile_et.1 diff --git a/util/com_err/error_message.c b/lib/com_err/error_message.c similarity index 100% rename from util/com_err/error_message.c rename to lib/com_err/error_message.c diff --git a/util/com_err/error_table.h b/lib/com_err/error_table.h similarity index 100% rename from util/com_err/error_table.h rename to lib/com_err/error_table.h diff --git a/util/com_err/et_c.awk b/lib/com_err/et_c.awk similarity index 100% rename from util/com_err/et_c.awk rename to lib/com_err/et_c.awk diff --git a/util/com_err/et_h.awk b/lib/com_err/et_h.awk similarity index 100% rename from util/com_err/et_h.awk rename to lib/com_err/et_h.awk diff --git a/util/com_err/et_name.c b/lib/com_err/et_name.c similarity index 100% rename from util/com_err/et_name.c rename to lib/com_err/et_name.c diff --git a/util/com_err/init_et.c b/lib/com_err/init_et.c similarity index 100% rename from util/com_err/init_et.c rename to lib/com_err/init_et.c diff --git a/util/com_err/internal.h b/lib/com_err/internal.h similarity index 100% rename from util/com_err/internal.h rename to lib/com_err/internal.h diff --git a/util/com_err/mit-sipb-copyright.h b/lib/com_err/mit-sipb-copyright.h similarity index 100% rename from util/com_err/mit-sipb-copyright.h rename to lib/com_err/mit-sipb-copyright.h diff --git a/util/ipx_sap_types b/lib/ipx_sap_types similarity index 100% rename from util/ipx_sap_types rename to lib/ipx_sap_types diff --git a/util/ncplib.c b/lib/ncplib.c similarity index 91% rename from util/ncplib.c rename to lib/ncplib.c index 10bc8ba..f152e20 100644 --- a/util/ncplib.c +++ b/lib/ncplib.c @@ -161,6 +161,43 @@ ipx_sscanf_node(char *buf, unsigned char node[6]) return 6; } +static int +ipx_sscanf_saddr(char *buf, struct sockaddr_ipx *target) +{ + char *p; + struct sockaddr_ipx addr; + + addr.sipx_family = AF_IPX; + addr.sipx_type = NCP_PTYPE; + + if (sscanf(buf, "%lx", &addr.sipx_network) != 1) + { + return 1; + } + addr.sipx_network = htonl(addr.sipx_network); + if ((p = strchr(buf, ':')) == NULL) + { + return 1; + } + p += 1; + if (ipx_sscanf_node(p, addr.sipx_node) != 6) + { + return 1; + } + if ((p = strchr(p, ':')) == NULL) + { + return 1; + } + p += 1; + if (sscanf(p, "%hx", &addr.sipx_port) != 1) + { + return 1; + } + addr.sipx_port = htons(addr.sipx_port); + *target = addr; + return 0; +} + void ipx_assign_node(IPXNode dest, IPXNode src) { @@ -222,224 +259,6 @@ ipx_recv(int sock, void *buf, int len, unsigned int flags, int timeout, timeout, err); } -static long -ipx_sap_find_nearest(int server_type, struct sockaddr_ipx *result, - char server_name[NCP_BINDERY_NAME_LEN]) -{ - struct sockaddr_ipx addr; - char data[1024]; - int sock; - int opt; - int packets; - int len; - - struct sap_server_ident *ident; - - if ((sock = socket(AF_IPX,SOCK_DGRAM,PF_IPX)) < 0) - { - if (errno == EINVAL) - { - return NCPL_ET_NO_IPX; - } - return errno; - } - - opt=1; - /* Permit broadcast output */ - if(setsockopt(sock,SOL_SOCKET,SO_BROADCAST, &opt,sizeof(opt))==-1) - { - goto finished; - } - - memzero(addr); - addr.sipx_family = AF_IPX; - addr.sipx_network = htonl(0x0); - addr.sipx_port = htons(0x0); - addr.sipx_type = IPX_SAP_PTYPE; - - if(bind(sock,(struct sockaddr*)&addr,sizeof(addr))==-1) - { - if (errno == EADDRNOTAVAIL) - { - errno = NCPL_ET_NO_INTERFACE; - } - goto finished; - } - - *(unsigned short *)data = htons(IPX_SAP_NEAREST_QUERY); - *(unsigned short *)&(data[2]) = htons(server_type); - - memzero(addr); - addr.sipx_family = AF_IPX; - addr.sipx_port = htons(IPX_SAP_PORT); - addr.sipx_type = IPX_SAP_PTYPE; - addr.sipx_network = htonl(0x0); - ipx_assign_node(addr.sipx_node, IPX_BROADCAST_NODE); - - if (sendto(sock, data, 4, 0, - (struct sockaddr *)&addr, sizeof(addr)) < 0) - { - goto finished; - } - - packets = 5; - do - { - long err; - len = ipx_recv(sock, data, 1024, 0, 1, &err); - if (len < 66) - { - packets = packets - 1; - continue; - } - } - while ( (ntohs(*((__u16 *)data)) != IPX_SAP_NEAREST_RESPONSE) - && (packets > 0)); - - if (packets == 0) - { - close(sock); - return NCPL_ET_NO_SERVER; - } - - ident = (struct sap_server_ident *)(data+2); - - result->sipx_family = AF_IPX; - result->sipx_network = ident->server_network; - result->sipx_port = ident->server_port; - ipx_assign_node(result->sipx_node, ident->server_node); - - memcpy(server_name, ident->server_name, sizeof(ident->server_name)); - - errno = 0; - - finished: - close(sock); - return errno; -} - -static int -ipx_make_reachable(IPXNet network) -{ - struct rtentry rt_def; - /* Router */ - struct sockaddr_ipx *sr = (struct sockaddr_ipx *)&rt_def.rt_gateway; - /* Target */ - struct sockaddr_ipx *st = (struct sockaddr_ipx *)&rt_def.rt_dst; - - struct ipx_rip_packet rip; - struct sockaddr_ipx addr; - int addrlen; - int sock; - int opt; - int res=-1; - int i; - int packets; - - if (geteuid() != 0) - { - errno = EPERM; - return -1; - } - - memzero(rip); - - sock = socket(AF_IPX, SOCK_DGRAM, PF_IPX); - - if (sock == -1) - { - if (errno == EINVAL) - { - return NCPL_ET_NO_IPX; - } - return errno; - } - - opt=1; - /* Permit broadcast output */ - if (setsockopt(sock, SOL_SOCKET, SO_BROADCAST, &opt, sizeof(opt)) != 0) - { - goto finished; - } - - memzero(addr); - addr.sipx_family = AF_IPX; - addr.sipx_network = htonl(0x0); - addr.sipx_port = htons(0x0); - addr.sipx_type = IPX_RIP_PTYPE; - - if (bind(sock, (struct sockaddr*)&addr, sizeof(addr)) != 0) - { - goto finished; - } - - addr.sipx_family = AF_IPX; - addr.sipx_port = htons(IPX_RIP_PORT); - addr.sipx_type = IPX_RIP_PTYPE; - addr.sipx_network = htonl(0x0); - ipx_assign_node(addr.sipx_node, IPX_BROADCAST_NODE); - - rip.operation = htons(IPX_RIP_REQUEST); - rip.rt[0].network = htonl(network); - - if (sendto(sock, &rip, sizeof(rip), 0, - (struct sockaddr *)&addr, sizeof(addr)) < 0) - { - goto finished; - } - - packets = 3; - do - { - long err; - int len; - - if (packets == 0) - { - goto finished; - } - - addrlen = sizeof(struct sockaddr_ipx); - - len = ipx_recvfrom(sock, &rip, sizeof(rip),0, sr, &addrlen, 1, - &err); - - if (len < sizeof(rip)) - { - packets = packets - 1; - continue; - } - } - while (ntohs(rip.operation) != IPX_RIP_RESPONSE); - - if (rip.rt[0].network != htonl(network)) - { - goto finished; - } - - rt_def.rt_flags = RTF_GATEWAY; - st->sipx_network = htonl(network); - st->sipx_family = AF_IPX; - sr->sipx_family = AF_IPX; - - i = 0; - do - { - res = ioctl(sock, SIOCADDRT, &rt_def); - i++; - } - while ((i < 5) && (res < 0) && (errno == EAGAIN)); - - finished: - close(sock); - - if (res != 0) - { - errno = ENETUNREACH; - } - return res; -} - static int install_wdog(struct ncp_conn *conn) { @@ -780,13 +599,8 @@ ncp_connect_addr(struct ncp_conn *conn, const struct sockaddr_ipx *target, if ((err = do_ncp_call(conn, sizeof(*h))) != 0) { - if ( (err != ENETUNREACH) - || (ipx_make_reachable(htonl(target->sipx_network)) != 0) - || ((err = do_ncp_call(conn, sizeof(*h))) != 0)) - { - close(ncp_sock); close(wdog_sock); - return err; - } + close(ncp_sock); close(wdog_sock); + return err; } if (wdog_needed != 0) @@ -817,103 +631,82 @@ ncp_connect_addr(struct ncp_conn *conn, const struct sockaddr_ipx *target, static long ncp_connect_any(struct ncp_conn *conn, int wdog_needed) { - struct sockaddr_ipx addr; - char name[NCP_BINDERY_NAME_LEN]; + struct sockaddr_ipx *addr; long result; + const char *server = NULL; + long err; - if ((result = ipx_sap_find_nearest(IPX_SAP_FILE_SERVER, - &addr, name)) != 0) + if ((addr = ncp_find_server(&server,NCP_BINDERY_FSERVER,&err)) == NULL) + { + return err; + } + + if ((result = ncp_connect_addr(conn, addr, wdog_needed)) != 0) { return result; } - - if ((result = ncp_connect_addr(conn, &addr, wdog_needed)) != 0) - { - return result; - } - strcpy(conn->server, name); + strcpy(conn->server, server); return 0; } struct sockaddr_ipx * ncp_find_fileserver(const char *server_name, long *err) { - char server[NCP_BINDERY_NAME_LEN]; - char nearest[NCP_BINDERY_NAME_LEN]; - struct nw_property prop; - struct prop_net_address *n_addr = (struct prop_net_address *)∝ - struct ncp_conn conn; + return ncp_find_server(&server_name, NCP_BINDERY_FSERVER, err); +} +struct sockaddr_ipx * +ncp_find_server(const char **server_name, int type, long *err) +{ + char command[256]; + char buf[128]; + char server[NCP_BINDERY_NAME_LEN+1]; static struct sockaddr_ipx result; + FILE *p; + int res; + char *n; - initialize_NCPL_error_table(); - if (strlen(server_name) >= sizeof(server)) + memset(server, 0, sizeof(server)); + + if (*server_name != NULL) { - *err = NCPL_ET_NAMETOOLONG; + strncpy(server, *server_name, sizeof(server)-1); + str_upper(server); + } + + sprintf(command, "nwsfind -t %d %s", type, server); + p = popen(command, "r"); + + if (p == NULL) + { + *err = errno; return NULL; } - strcpy(server, server_name); - str_upper(server); + fgets(buf, sizeof(buf), p); - if ((*err = ipx_sap_find_nearest(IPX_SAP_FILE_SERVER, - &result, nearest)) != 0) + if (buf[strlen(buf)] - 1 == '\n'); { + buf[strlen(buf)] = '\0'; + } + + if (((res = pclose(p)) != 0) || (ipx_sscanf_saddr(buf, &result) != 0)) + { + *err = (*server_name != NULL) + ? NCPL_ET_HOST_UNKNOWN : NCPL_ET_NO_SERVER; return NULL; } - /* We have to ask the nearest server for our wanted server */ - - memzero(conn); - if ((*err = ncp_connect_addr(&conn, &result, 0)) != 0) + if (*server_name == NULL) { - return NULL; + if ((n = strchr(buf, ' ')) == NULL) + { + *err = NCPL_ET_HOST_UNKNOWN; + return NULL; + } + *server_name = n; } - /* The following optimization should have been done before - ncp_connect_addr. This would be convenient if there was a - simple way to find out whether there is a route to the - server. Parsing /proc/net/ipx_route is not too nice, so we - just connect to the server and immediately disconnect - again. This way we also find out if the server still has - free connection slots. */ - - if (strcmp(server, nearest) == 0) - { - /* Our wanted server answered the SAP GNS request, so - use it */ - ncp_do_close(&conn); - errno = 0; - return &result; - } - - if (ncp_read_property_value(&conn, NCP_BINDERY_FSERVER, server, 1, - "NET_ADDRESS", &prop) != 0) - { - ncp_do_close(&conn); - *err = NCPL_ET_HOST_UNKNOWN; - return NULL; - } - - if ((*err = ncp_do_close(&conn)) != 0) - { - return NULL; - } - - result.sipx_family = AF_IPX; - result.sipx_network = n_addr->network; - result.sipx_port = n_addr->port; - ipx_assign_node(result.sipx_node, n_addr->node); - - /* To make the final server reachable, we connect again. See - above. (When can we rely on all users running ipxd??? :-)) */ - memzero(conn); - if ( ((*err = ncp_connect_addr(&conn, &result, 0)) != 0) - || ((*err = ncp_do_close(&conn)) != 0)) - { - return NULL; - } - return &result; } diff --git a/util/ncplib_err.et b/lib/ncplib_err.et similarity index 100% rename from util/ncplib_err.et rename to lib/ncplib_err.et diff --git a/util/nwcrypt.c b/lib/nwcrypt.c similarity index 100% rename from util/nwcrypt.c rename to lib/nwcrypt.c diff --git a/man/ncopy.1 b/man/ncopy.1 index b1b99c6..bddb22b 100644 --- a/man/ncopy.1 +++ b/man/ncopy.1 @@ -90,7 +90,7 @@ option to .B ncpmount(8), ncpumount(8) .SH CREDITS -ncopy was written by Brian G. Reid (breid@tim.com) and -Tom C. Henderson (thenderson@tim.com). -Many thanks to Volker Lendecke (lendecke@namu01.gwdg.de) for the ncpfs -and ncplib which made ncopy possible. +ncopy was written by Brian G. Reid (breid@tim.com) and Tom +C. Henderson (thenderson@tim.com). Many thanks to Volker Lendecke +(lendecke@math.uni-goettingen.de) for the ncpfs and ncplib which made +ncopy possible. diff --git a/man/ncpmount.8 b/man/ncpmount.8 index 30b15c5..afa1d18 100644 --- a/man/ncpmount.8 +++ b/man/ncpmount.8 @@ -291,5 +291,5 @@ The encryption code was taken from Dr. Dobbs's Journal 11/93. There Pawel Szczerbina described it in an article on NCP. The ncpfs code was initially hacked from smbfs by Volker Lendecke -(lendecke@namu01.gwdg.de). smbfs was put together by Paal-Kr. Engstad +(lendecke@math.uni-goettingen.de). smbfs was put together by Paal-Kr. Engstad (pke@engstad.ingok.hitos.no) and later polished by Volker. diff --git a/man/nprint.1 b/man/nprint.1 index 850d37a..c583cf8 100644 --- a/man/nprint.1 +++ b/man/nprint.1 @@ -219,4 +219,4 @@ printed if a printer operator has put in the correct form. .B nwclient(5), slist(1), pqlist(1), ncpmount(8), ncpumount(8) .SH CREDITS -nprint was written by Volker Lendecke (lendecke@namu01.gwdg.de) +nprint was written by Volker Lendecke (lendecke@math.uni-goettingen.de) diff --git a/man/nwauth.1 b/man/nwauth.1 new file mode 100644 index 0000000..d1b5adb --- /dev/null +++ b/man/nwauth.1 @@ -0,0 +1,69 @@ +.TH NWAUTH 1 10/27/1996 nwauth nwauth +.SH NAME +nwauth \- Verify username/password +.SH SYNOPSIS +.B nwauth +[ +.B -h +] [ +.B -S +.I server +] [ +.B -U +.I user name +] [ +.B -P +.I password + | +.B -n +] +.SH DESCRIPTION +.B nwauth +does nothing but logging into a NetWare server. If the login was +successful, an error code of 0 is returned. If the login was not +successful, an error code of 1 is returned. It was designed for +use by other programs who want authenticate users via a NetWare +server. + +nwauth +.B always +expects a password on stdin. If the stdin is a tty, then the user is +prompted for a password. Otherwise nwauth simply reads stdin for a +password. + +.B nwauth +looks up the file +.I $HOME/.nwclient +to find a file server and a user name. See nwclient(5) for more +information. Please note that the access permissions of .nwclient MUST +be 600, for security reasons. + +.SH OPTIONS + +.B -h +.RS 3 +.B -h +is used to print a short help text. +.RE + +.B -S +.I server +.RS 3 +.B server +is the name of the server you want to use. +.RE + +.B -U +.I user name +.RS 3 +If the user name your NetWare administrator gave to you differs +from your unix user-id, you should use +.B -U +to tell the server about your NetWare user name. +.RE + +.SH SEE ALSO +.B nwclient(5) + +.SH CREDITS +nwauth was written by Volker Lendecke (lendecke@math.uni-goettingen.de) diff --git a/man/nwsfind.1 b/man/nwsfind.1 new file mode 100644 index 0000000..f559eec --- /dev/null +++ b/man/nwsfind.1 @@ -0,0 +1,36 @@ +.TH NWSFIND 1 10/27/1996 nwsfind nwsfind +.SH NAME +nwsfind \- Find a NetWare Server +.SH SYNOPSIS +.B nwsfind +[ +.B -t +.I type +] [ +.I name +] +.SH DESCRIPTION +.B nwsfind +searches for a NetWare server and finds a route to this +server. nwsfind was written to be setuid root. It is called from +within the ncp library, so that it is possible that normal users use +the utilities. + +.SH OPTIONS +.B name +.RS 3 +If you look for a specific server, you should give nwsfind this +argument. If you omit it, nwsfind looks for the server nearest to you. +.RE + +.B -t +.I type +.RS 3 +By default nwsfind looks for file servers. In case you want to look up +another server type, you have to specify its numerical type as +.B type. +.RE + + +.SH CREDITS +nwsfind was written by Volker Lendecke (lendecke@math.uni-goettingen.de) diff --git a/man/pqlist.1 b/man/pqlist.1 index 5779a8c..3334eb1 100644 --- a/man/pqlist.1 +++ b/man/pqlist.1 @@ -102,4 +102,4 @@ this conversion by .B nwclient(5), nprint(1), slist(1), ncpmount(8), ncpumount(8) .SH CREDITS -pqlist was written by Volker Lendecke (lendecke@namu01.gwdg.de) +pqlist was written by Volker Lendecke (lendecke@math.uni-goettingen.de) diff --git a/man/pserver.1 b/man/pserver.1 index de39c7b..0cb3dd2 100644 --- a/man/pserver.1 +++ b/man/pserver.1 @@ -1,4 +1,4 @@ -.TH PSERVER 1 02/10/1996 pserver pserver +.TH PSERVER 1 10/22/1996 pserver pserver .SH NAME pserver \- NetWare print server .SH SYNOPSIS @@ -101,6 +101,13 @@ process, and feeds the job file to stdin. .I command is the printing command that is executed for each job. The default command is 'lpr'. + +You can insert several flags into the command, preceded by %. These +are replaced with values retrieved from the queue structure for the +print job. + +%u: This field will be replaced by the name of the user who posted +this print job. .RE .B -j @@ -139,4 +146,4 @@ diagnostic messages that are printed when a error occurs. .B nwclient(5), slist(1), pqlist(1), ncpmount(8), ncpumount(8) .SH CREDITS -pserver was written by Volker Lendecke (lendecke@namu01.gwdg.de) +pserver was written by Volker Lendecke (lendecke@math.uni-goettingen.de) diff --git a/man/slist.1 b/man/slist.1 index 13065a6..0c3e28e 100644 --- a/man/slist.1 +++ b/man/slist.1 @@ -40,4 +40,4 @@ List all available Netware servers on your Network, that begin with an "I". .B ncpmount(8), ncpumount(8), pqlist(1), nprint(1) .SH CREDITS -slist was written by Volker Lendecke (lendecke@namu01.gwdg.de) +slist was written by Volker Lendecke (lendecke@math.uni-goettingen.de) diff --git a/ncpfs-2.0.6.lsm b/ncpfs-2.0.7.lsm similarity index 83% rename from ncpfs-2.0.6.lsm rename to ncpfs-2.0.7.lsm index d930a5a..2cd938c 100644 --- a/ncpfs-2.0.6.lsm +++ b/ncpfs-2.0.7.lsm @@ -1,7 +1,7 @@ Begin3 Title: ncpfs -Version: 2.0.6 -Entered-date: 08. August 1996 +Version: 2.0.7 +Entered-date: 27. October 1996 Description: With ncpfs you can mount volumes of your netware server under Linux. You can also print to netware print queues and spool netware print queues to the @@ -13,7 +13,7 @@ Author: lendecke@namu01.Num.Math.Uni-Goettingen.de (Volker Lendecke) Maintained-by: lendecke@namu01.Num.Math.Uni-Goettingen.de (Volker Lendecke) Primary-site: ftp.gwdg.de:/pub/linux/misc/ncpfs Alternate-site: sunsite.unc.edu:/pub/Linux/system/Filesystems/ncpfs - ~136k ncpfs-2.0.6.tgz - ~ 1k ncpfs-2.0.6.lsm + ~148k ncpfs-2.0.7.tgz + ~ 1k ncpfs-2.0.7.lsm Copying-policy: GPL End diff --git a/sutil/Makefile b/sutil/Makefile new file mode 100644 index 0000000..638f2de --- /dev/null +++ b/sutil/Makefile @@ -0,0 +1,42 @@ +# +# Makefile for the linux ncp-filesystem routines. +# + +UTILS = ncpmount ncpumount nwsfind + +CC = gcc + +default: + make -C .. + +all: $(UTILS) + +install: all + for i in $(UTILS); \ + do install $$i -m 4755 $(BINDIR); done + +$(UTILS): %: %.o libncp.a + $(CC) -o $@ $(addsuffix .o,$@) -L. -lncp -L../lib -lcom_err + +ncplib.o: ncplib.c ncplib.h + $(CC) $(CFLAGS) -finline-functions -c ncplib.c + +libncp.a: ncplib.o ../lib/ncplib_err.o + ar r libncp.a ncplib.o ../lib/ncplib_err.o + +dep: + $(CPP) -M $(INCLUDES) *.c > .depend + +clean: + rm -f *.o *~ libncp.a $(UTILS) + +mrproper: clean + rm -f .depend + +# +# include a dependency file if one exists +# +ifeq (.depend,$(wildcard .depend)) +include .depend +endif + diff --git a/sutil/ipxlib.h b/sutil/ipxlib.h new file mode 100644 index 0000000..ac243b0 --- /dev/null +++ b/sutil/ipxlib.h @@ -0,0 +1,93 @@ +/* + * ipxlib.h + * + * Copyright (C) 1995 by Volker Lendecke + * + */ + +#ifndef _IPXLIB_H +#define _IPXLIB_H + + +#include +#include +#include +#include +#include + +typedef unsigned long IPXNet; +typedef unsigned short IPXPort; +typedef unsigned char IPXNode[IPX_NODE_LEN]; + +#define IPX_USER_PTYPE (0x00) +#define IPX_RIP_PTYPE (0x01) +#define IPX_SAP_PTYPE (0x04) +#define IPX_AUTO_PORT (0x0000) +#define IPX_SAP_PORT (0x0452) +#define IPX_RIP_PORT (0x0453) + +#define IPX_SAP_GENERAL_QUERY (0x0001) +#define IPX_SAP_GENERAL_RESPONSE (0x0002) +#define IPX_SAP_NEAREST_QUERY (0x0003) +#define IPX_SAP_NEAREST_RESPONSE (0x0004) + +#define IPX_SAP_FILE_SERVER (0x0004) + +struct sap_query { + unsigned short query_type; /* net order */ + unsigned short server_type; /* net order */ +}; + +struct sap_server_ident { + unsigned short server_type __attribute__ ((packed)); + char server_name[48] __attribute__ ((packed)); + IPXNet server_network __attribute__ ((packed)); + IPXNode server_node __attribute__ ((packed)); + IPXPort server_port __attribute__ ((packed)); + unsigned short intermediate_network __attribute__ ((packed)); +}; + +#define IPX_RIP_REQUEST (0x1) +#define IPX_RIP_RESPONSE (0x2) + +struct ipx_rip_packet { + __u16 operation __attribute__ ((packed)); + struct ipx_rt_def { + __u32 network __attribute__ ((packed)); + __u16 hops __attribute__ ((packed)); + __u16 ticks __attribute__ ((packed)); + } rt[1] __attribute__ ((packed)); +}; + +#define IPX_BROADCAST_NODE ("\xff\xff\xff\xff\xff\xff") +#define IPX_THIS_NODE ("\0\0\0\0\0\0") +#define IPX_THIS_NET (0) + +#ifndef IPX_NODE_LEN +#define IPX_NODE_LEN (6) +#endif + +void +ipx_print_node(IPXNode node); +void +ipx_print_network(IPXNet net); +void +ipx_print_port(IPXPort port); +void +ipx_print_saddr(struct sockaddr_ipx* sipx); +void +ipx_fprint_node(FILE *file, IPXNode node); +void +ipx_fprint_network(FILE *file, IPXNet net); +void +ipx_fprint_port(FILE *file, IPXPort port); +void +ipx_fprint_saddr(FILE *file, struct sockaddr_ipx* sipx); +int +ipx_sscanf_node(char *buf, unsigned char node[IPX_NODE_LEN]); +void +ipx_assign_node(IPXNode dest, IPXNode src); +int +ipx_node_equal(IPXNode n1,IPXNode n2); + +#endif /* _IPXLIB_H */ diff --git a/sutil/ncplib.c b/sutil/ncplib.c new file mode 100644 index 0000000..7f09950 --- /dev/null +++ b/sutil/ncplib.c @@ -0,0 +1,1927 @@ +/* + * ncplib.c + * + * Copyright (C) 1995, 1996 by Volker Lendecke + * + */ + +#include "ncplib.h" +#include "ncplib_err.h" + +typedef __u8 byte; +typedef __u16 word; +typedef __u32 dword; + +#include +/* #include */ /* generates a warning here */ +extern pid_t wait(int *); +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static long +ncp_negotiate_buffersize(struct ncp_conn *conn, + int size, int *target); +static long +ncp_login_object(struct ncp_conn *conn, + const unsigned char *username, + int login_type, + const unsigned char *password); + +static long +ncp_do_close(struct ncp_conn *conn); + +void +str_upper(char *name) +{ + while (*name) { + *name = toupper(*name); + name = name + 1; + } +} + +/* I know it's terrible to include a .c file here, but I want to keep + the file nwcrypt.c intact and separate for copyright reasons */ +#include "nwcrypt.c" + +void +ipx_fprint_node(FILE* file,IPXNode node) +{ + fprintf(file,"%02X%02X%02X%02X%02X%02X", + (unsigned char)node[0], + (unsigned char)node[1], + (unsigned char)node[2], + (unsigned char)node[3], + (unsigned char)node[4], + (unsigned char)node[5] + ); +} + +void +ipx_fprint_network(FILE* file,IPXNet net) +{ + fprintf(file,"%08lX",ntohl(net)); +} + +void +ipx_fprint_port(FILE* file,IPXPort port) +{ + fprintf(file,"%04X",ntohs(port)); +} + +void +ipx_fprint_saddr(FILE* file,struct sockaddr_ipx* sipx) +{ + ipx_fprint_network(file,sipx->sipx_network); + fprintf(file,":"); + ipx_fprint_node(file,sipx->sipx_node); + fprintf(file,":"); + ipx_fprint_port(file,sipx->sipx_port); +} + +void +ipx_print_node(IPXNode node) +{ + ipx_fprint_node(stdout,node); +} + +void +ipx_print_network(IPXNet net) +{ + ipx_fprint_network(stdout,net); +} + +void +ipx_print_port(IPXPort port) +{ + ipx_fprint_port(stdout,port); +} + +void +ipx_print_saddr(struct sockaddr_ipx* sipx) +{ + ipx_fprint_saddr(stdout,sipx); +} + +int +ipx_sscanf_node(char *buf, unsigned char node[6]) +{ + int i; + int n[6]; + + if ((i = sscanf(buf, "%2x%2x%2x%2x%2x%2x", + &(n[0]), &(n[1]), &(n[2]), + &(n[3]), &(n[4]), &(n[5]))) != 6) + { + return i; + } + + for (i=0; i<6; i++) + { + node[i] = n[i]; + } + return 6; +} + +void +ipx_assign_node(IPXNode dest, IPXNode src) +{ + memcpy(dest, src, IPX_NODE_LEN); +} + +int +ipx_node_equal(IPXNode n1,IPXNode n2) +{ + return memcmp(n1,n2, IPX_NODE_LEN)==0; +} + +static int +ipx_recvfrom(int sock, void *buf, int len, unsigned int flags, + struct sockaddr_ipx *sender, int *addrlen, int timeout, + long *err) +{ + fd_set rd, wr, ex; + struct timeval tv; + int result; + + FD_ZERO(&rd); FD_ZERO(&wr); FD_ZERO(&ex); + FD_SET(sock, &rd); + + tv.tv_sec = timeout; + tv.tv_usec = 0; + + if ((result = select(sock+1, &rd, &wr, &ex, &tv)) == -1) + { + *err = errno; + return -1; + } + + if (FD_ISSET(sock, &rd)) + { + result = recvfrom(sock, buf, len, flags, + (struct sockaddr *)sender, addrlen); + } + else + { + result = -1; + errno = ETIMEDOUT; + } + if (result < 0) + { + *err = errno; + } + return result; +} + +static int +ipx_recv(int sock, void *buf, int len, unsigned int flags, int timeout, + long *err) +{ + struct sockaddr_ipx sender; + int addrlen = sizeof(sender); + + return ipx_recvfrom(sock, buf, len, flags, &sender, &addrlen, + timeout, err); +} + +static long +ipx_sap_find_nearest(int server_type, struct sockaddr_ipx *result, + char server_name[NCP_BINDERY_NAME_LEN]) +{ + struct sockaddr_ipx addr; + char data[1024]; + int sock; + int opt; + int packets; + int len; + + struct sap_server_ident *ident; + + if ((sock = socket(AF_IPX,SOCK_DGRAM,PF_IPX)) < 0) + { + if (errno == EINVAL) + { + return NCPL_ET_NO_IPX; + } + return errno; + } + + opt=1; + /* Permit broadcast output */ + if(setsockopt(sock,SOL_SOCKET,SO_BROADCAST, &opt,sizeof(opt))==-1) + { + goto finished; + } + + memzero(addr); + addr.sipx_family = AF_IPX; + addr.sipx_network = htonl(0x0); + addr.sipx_port = htons(0x0); + addr.sipx_type = IPX_SAP_PTYPE; + + if(bind(sock,(struct sockaddr*)&addr,sizeof(addr))==-1) + { + if (errno == EADDRNOTAVAIL) + { + errno = NCPL_ET_NO_INTERFACE; + } + goto finished; + } + + *(unsigned short *)data = htons(IPX_SAP_NEAREST_QUERY); + *(unsigned short *)&(data[2]) = htons(server_type); + + memzero(addr); + addr.sipx_family = AF_IPX; + addr.sipx_port = htons(IPX_SAP_PORT); + addr.sipx_type = IPX_SAP_PTYPE; + addr.sipx_network = htonl(0x0); + ipx_assign_node(addr.sipx_node, IPX_BROADCAST_NODE); + + if (sendto(sock, data, 4, 0, + (struct sockaddr *)&addr, sizeof(addr)) < 0) + { + goto finished; + } + + packets = 5; + do + { + long err; + len = ipx_recv(sock, data, 1024, 0, 1, &err); + if (len < 66) + { + packets = packets - 1; + continue; + } + } + while ( (ntohs(*((__u16 *)data)) != IPX_SAP_NEAREST_RESPONSE) + && (packets > 0)); + + if (packets == 0) + { + close(sock); + return NCPL_ET_NO_SERVER; + } + + ident = (struct sap_server_ident *)(data+2); + + result->sipx_family = AF_IPX; + result->sipx_network = ident->server_network; + result->sipx_port = ident->server_port; + ipx_assign_node(result->sipx_node, ident->server_node); + + memcpy(server_name, ident->server_name, sizeof(ident->server_name)); + + errno = 0; + + finished: + close(sock); + return errno; +} + +static int +ipx_make_reachable(IPXNet network) +{ + struct rtentry rt_def; + /* Router */ + struct sockaddr_ipx *sr = (struct sockaddr_ipx *)&rt_def.rt_gateway; + /* Target */ + struct sockaddr_ipx *st = (struct sockaddr_ipx *)&rt_def.rt_dst; + + struct ipx_rip_packet rip; + struct sockaddr_ipx addr; + int addrlen; + int sock; + int opt; + int res=-1; + int i; + int packets; + + if (geteuid() != 0) + { + errno = EPERM; + return -1; + } + + memzero(rip); + + sock = socket(AF_IPX, SOCK_DGRAM, PF_IPX); + + if (sock == -1) + { + if (errno == EINVAL) + { + return NCPL_ET_NO_IPX; + } + return errno; + } + + opt=1; + /* Permit broadcast output */ + if (setsockopt(sock, SOL_SOCKET, SO_BROADCAST, &opt, sizeof(opt)) != 0) + { + goto finished; + } + + memzero(addr); + addr.sipx_family = AF_IPX; + addr.sipx_network = htonl(0x0); + addr.sipx_port = htons(0x0); + addr.sipx_type = IPX_RIP_PTYPE; + + if (bind(sock, (struct sockaddr*)&addr, sizeof(addr)) != 0) + { + goto finished; + } + + addr.sipx_family = AF_IPX; + addr.sipx_port = htons(IPX_RIP_PORT); + addr.sipx_type = IPX_RIP_PTYPE; + addr.sipx_network = htonl(0x0); + ipx_assign_node(addr.sipx_node, IPX_BROADCAST_NODE); + + rip.operation = htons(IPX_RIP_REQUEST); + rip.rt[0].network = htonl(network); + + if (sendto(sock, &rip, sizeof(rip), 0, + (struct sockaddr *)&addr, sizeof(addr)) < 0) + { + goto finished; + } + + packets = 3; + do + { + long err; + int len; + + if (packets == 0) + { + goto finished; + } + + addrlen = sizeof(struct sockaddr_ipx); + + len = ipx_recvfrom(sock, &rip, sizeof(rip),0, sr, &addrlen, 1, + &err); + + if (len < sizeof(rip)) + { + packets = packets - 1; + continue; + } + } + while (ntohs(rip.operation) != IPX_RIP_RESPONSE); + + if (rip.rt[0].network != htonl(network)) + { + goto finished; + } + + rt_def.rt_flags = RTF_GATEWAY; + st->sipx_network = htonl(network); + st->sipx_family = AF_IPX; + sr->sipx_family = AF_IPX; + + i = 0; + do + { + res = ioctl(sock, SIOCADDRT, &rt_def); + i++; + } + while ((i < 5) && (res < 0) && (errno == EAGAIN)); + + finished: + close(sock); + + if (res != 0) + { + errno = ENETUNREACH; + } + return res; +} + +static int +install_wdog(struct ncp_conn *conn) +{ + int parent_pid = getpid(); + int pid; + int sock = conn->wdog_sock; + + char buf[1024]; + struct sockaddr_ipx sender; + int sizeofaddr = sizeof(struct sockaddr_ipx); + int pktsize; + + + if ((pid = fork()) < 0) + { + return -1; + } + + if (pid != 0) + { + /* Parent, should go on as usual */ + conn->wdog_pid = pid; + return 0; + } + + while (1) + { + long err; + /* every 120 seconds we look if our parent is + still alive */ + pktsize = ipx_recvfrom(sock, buf, sizeof(buf), 0, + &sender, &sizeofaddr, 120, &err); + + if (getppid() != parent_pid) + { + /* our parent has died, so nothing to do + anymore */ + exit(0); + } + + if ( (pktsize != 2) + || (buf[1] != '?')) + { + continue; + } + + buf[1] = 'Y'; + pktsize = sendto(sock, buf, 2, 0, + (struct sockaddr *)&sender, + sizeof(sender)); + } +} + +#define ncp_printf printf + +static void +assert_conn_locked(struct ncp_conn *conn); + +static void +assert_conn_not_locked(struct ncp_conn *conn) +{ + if (conn->lock != 0) + { + ncp_printf("ncpfs: conn already locked!\n"); + } +} + +static void +ncp_lock_conn(struct ncp_conn *conn) +{ + assert_conn_not_locked(conn); + conn->lock = 1; +} + +static void +ncp_unlock_conn(struct ncp_conn *conn) +{ + assert_conn_locked(conn); + conn->lock = 0; +} + +static long +do_ncp_call(struct ncp_conn *conn, int request_size) +{ + struct ncp_request_header request = + *((struct ncp_request_header *)(&(conn->packet))); + + int result; + int retries = 20; + int len; + long err; + + while (retries > 0) + { + struct ncp_reply_header reply; + struct sockaddr_ipx sender; + int sizeofaddr = sizeof(sender); + + retries -= 1; + + result = sendto(conn->ncp_sock, conn->packet, + request_size, + 0, (struct sockaddr *)&(conn->i.addr), + sizeof(conn->i.addr)); + + if (result < 0) + { + return errno; + } + + re_select: + len = ipx_recvfrom(conn->ncp_sock, + (char *)&reply, sizeof(reply), + MSG_PEEK, &sender, &sizeofaddr, 3, &err); + + if ((len < 0) && (err == ETIMEDOUT)) + { + continue; + } + if (len < 0) + { + return err; + } + + if ( /* Is the sender wrong? */ + (memcmp(&sender.sipx_node, + &(conn->i.addr.sipx_node), 6) != 0) + || (sender.sipx_port != conn->i.addr.sipx_port) + + /* Did the sender send a positive acknowledge? */ + || ( (len == sizeof(reply)) + && (reply.type == NCP_POSITIVE_ACK)) + + /* Did we get a bogus answer? */ + || ( (len < sizeof(reply)) + || (reply.type != NCP_REPLY) + || ( (request.type != NCP_ALLOC_SLOT_REQUEST) + && ( (reply.sequence != request.sequence) + || (reply.conn_low != request.conn_low) + || (reply.conn_high != request.conn_high))))) + { + /* Then throw away the packet */ + ipx_recv(conn->ncp_sock, (char *)&reply, sizeof(reply), + 0, 1, &err); + goto re_select; + } + + ipx_recv(conn->ncp_sock, conn->packet, NCP_PACKET_SIZE, + 0, 1, &err); + conn->reply_size = len; + return 0; + } + return ETIMEDOUT; +} + +static int +ncp_mount_request(struct ncp_conn *conn, int function) +{ + struct ncp_request_header *h + = (struct ncp_request_header *)(conn->packet); + struct ncp_reply_header *reply + = (struct ncp_reply_header *)(conn->packet); + struct ncp_ioctl_request request; + + int result; + + assert_conn_locked(conn); + + if (conn->has_subfunction != 0) + { + *(__u16 *)&(h->data[0]) + = htons(conn->current_size + - sizeof(struct ncp_request_header) - 2); + } + + request.function = function; + request.size = conn->current_size; + request.data = conn->packet; + + if ((result = ioctl(conn->mount_fid,NCP_IOC_NCPREQUEST, &request)) < 0) + { + return result; + } + + conn->completion = reply->completion_code; + conn->conn_status = reply->connection_state; + conn->ncp_reply_size = result - sizeof(struct ncp_reply_header); + + if ((reply->completion_code != 0) && (conn->verbose != 0)) + { + ncp_printf("ncp_request_error: %d\n", reply->completion_code); + } + return reply->completion_code == 0 ? 0 : NCPL_ET_REQUEST_ERROR; +} + +static long +ncp_temp_request(struct ncp_conn *conn, int function) +{ + struct ncp_request_header *h + = (struct ncp_request_header *)&(conn->packet); + struct ncp_reply_header *r + = (struct ncp_reply_header *)&(conn->packet); + + long err; + + assert_conn_locked(conn); + + if (conn->has_subfunction != 0) + { + *(__u16 *)&(h->data[0]) + = htons(conn->current_size + - sizeof(struct ncp_request_header) - 2); + } + + h->type = NCP_REQUEST; + + conn->sequence += 1; + h->sequence = conn->sequence; + h->conn_low = (conn->i.connection) & 0xff; + h->conn_high = ((conn->i.connection) & 0xff00) >> 8; + h->task = 1; + h->function = function; + + if ((err = do_ncp_call(conn, conn->current_size)) != 0) + { + return err; + } + + conn->completion = r->completion_code; + conn->conn_status = r->connection_state; + conn->ncp_reply_size = + conn->reply_size - sizeof(struct ncp_reply_header); + + if ((r->completion_code != 0) && (conn->verbose != 0)) + { + ncp_printf("ncp_completion_code: %d\n", r->completion_code); + } + return r->completion_code == 0 ? 0 : NCPL_ET_REQUEST_ERROR; +} + +static long +ncp_connect_addr(struct ncp_conn *conn, const struct sockaddr_ipx *target, + int wdog_needed) +{ + struct ncp_request_header *h = + (struct ncp_request_header *)&(conn->packet); + + struct sockaddr_ipx addr; + int addrlen; + + int ncp_sock, wdog_sock; + long err; + + conn->is_connected = NOT_CONNECTED; + conn->verbose = 0; + + if ((ncp_sock = socket(AF_IPX, SOCK_DGRAM, PF_IPX)) == -1) + { + return errno; + } + + if ((wdog_sock = socket(AF_IPX, SOCK_DGRAM, PF_IPX)) == -1) + { + return errno; + } + + addr.sipx_family = AF_IPX; + addr.sipx_port = htons(0x0); + addr.sipx_type = NCP_PTYPE; + addr.sipx_network = IPX_THIS_NET; + ipx_assign_node(addr.sipx_node, IPX_THIS_NODE); + + addrlen = sizeof(addr); + + if ( (bind(ncp_sock, (struct sockaddr *)&addr, sizeof(addr)) == -1) + || (getsockname(ncp_sock, (struct sockaddr *)&addr, &addrlen)==-1)) + { + int saved_errno = errno; + close(ncp_sock); close(wdog_sock); + return saved_errno; + } + + addr.sipx_port = htons(ntohs(addr.sipx_port) + 1); + + if (bind(wdog_sock, (struct sockaddr *)&addr, sizeof(addr)) == -1) + { + int saved_errno = errno; + close(ncp_sock); close(wdog_sock); + return saved_errno; + } + + conn->ncp_sock = ncp_sock; + conn->wdog_sock = wdog_sock; + + h->type = NCP_ALLOC_SLOT_REQUEST; + + conn->sequence = 0; + conn->i.addr = *target; + h->sequence = conn->sequence; + h->conn_low = 0xff; + h->conn_high = 0xff; + h->task = 1; + h->function = 0; + + if ((err = do_ncp_call(conn, sizeof(*h))) != 0) + { + if ( (err != ENETUNREACH) + || (ipx_make_reachable(htonl(target->sipx_network)) != 0) + || ((err = do_ncp_call(conn, sizeof(*h))) != 0)) + { + close(ncp_sock); close(wdog_sock); + return err; + } + } + + if (wdog_needed != 0) + { + install_wdog(conn); + } + else + { + conn->wdog_pid = 0; + } + + conn->sequence = 0; + conn->i.connection = h->conn_low + (h->conn_high * 256); + conn->is_connected = CONN_TEMPORARY; + + if ( (ncp_negotiate_buffersize(conn, 1024, + &(conn->i.buffer_size)) != 0) + || (conn->i.buffer_size < 512) + || (conn->i.buffer_size > 1024)) + { + ncp_do_close(conn); + return -1; + } + + return 0; +} + +static long +ncp_connect_any(struct ncp_conn *conn, int wdog_needed) +{ + struct sockaddr_ipx addr; + char name[NCP_BINDERY_NAME_LEN]; + long result; + + if ((result = ipx_sap_find_nearest(IPX_SAP_FILE_SERVER, + &addr, name)) != 0) + { + return result; + } + + if ((result = ncp_connect_addr(conn, &addr, wdog_needed)) != 0) + { + return result; + } + strcpy(conn->server, name); + return 0; +} + +struct sockaddr_ipx * +ncp_find_fileserver(char *server_name, long *err) +{ + return ncp_find_server(&server_name, NCP_BINDERY_FSERVER, err); +} + +struct sockaddr_ipx * +ncp_find_server(char **server_name, int type, long *err) +{ + char server[NCP_BINDERY_NAME_LEN+1]; + static char nearest[NCP_BINDERY_NAME_LEN+1]; + struct nw_property prop; + struct prop_net_address *n_addr = (struct prop_net_address *)∝ + struct ncp_conn conn; + + static struct sockaddr_ipx result; + + initialize_NCPL_error_table(); + + memset(server, 0, sizeof(server)); + memset(nearest, 0, sizeof(nearest)); + + if (*server_name != NULL) + { + if (strlen(*server_name) >= sizeof(server)) + { + *err = NCPL_ET_NAMETOOLONG; + return NULL; + } + + strcpy(server, *server_name); + str_upper(server); + } + + if ((*err = ipx_sap_find_nearest(type, &result, nearest)) != 0) + { + return NULL; + } + + /* We have to ask the nearest server for our wanted server */ + + memzero(conn); + if ((*err = ncp_connect_addr(&conn, &result, 0)) != 0) + { + return NULL; + } + + if (*server_name == NULL) + { + *server_name = nearest; + ncp_do_close(&conn); + errno = 0; + return &result; + } + + /* The following optimization should have been done before + ncp_connect_addr. This would be convenient if there was a + simple way to find out whether there is a route to the + server. Parsing /proc/net/ipx_route is not too nice, so we + just connect to the server and immediately disconnect + again. This way we also find out if the server still has + free connection slots. */ + + if (strcmp(server, nearest) == 0) + { + /* Our wanted server answered the SAP GNS request, so + use it */ + ncp_do_close(&conn); + errno = 0; + return &result; + } + + if (ncp_read_property_value(&conn, type, server, 1, + "NET_ADDRESS", &prop) != 0) + { + ncp_do_close(&conn); + *err = NCPL_ET_HOST_UNKNOWN; + return NULL; + } + + if ((*err = ncp_do_close(&conn)) != 0) + { + return NULL; + } + + result.sipx_family = AF_IPX; + result.sipx_network = n_addr->network; + result.sipx_port = n_addr->port; + ipx_assign_node(result.sipx_node, n_addr->node); + + /* To make the final server reachable, we connect again. See + above. (When can we rely on all users running ipxd??? :-)) */ + memzero(conn); + if ( ((*err = ncp_connect_addr(&conn, &result, 0)) != 0) + || ((*err = ncp_do_close(&conn)) != 0)) + { + return NULL; + } + + return &result; +} + +static long +ncp_open_temporary(struct ncp_conn *conn, + struct ncp_conn_spec *spec) +{ + struct sockaddr_ipx *addr; + long err; + + if (spec == NULL) + { + return ncp_connect_any(conn, 1); + } + + if ((addr = ncp_find_fileserver(spec->server, &err)) == NULL) + { + return err; + } + + if ((err = ncp_connect_addr(conn, addr, 1)) != 0) + { + return err; + } + + strcpy(conn->server, spec->server); + + if (strlen(spec->user) != 0) + { + if (ncp_login_object(conn, spec->user, spec->login_type, + spec->password) != 0) + { + ncp_do_close(conn); + return EACCES; + } + strcpy(conn->user, spec->user); + } + + return 0; +} + +char * +ncp_find_permanent(const struct ncp_conn_spec *spec) +{ + FILE *mtab; + struct ncp_conn_ent *conn_ent; + char *result = NULL; + int mount_fid; + struct ncp_fs_info i; + + initialize_NCPL_error_table(); + + if ((mtab = fopen(MOUNTED, "r")) == NULL) + { + return NULL; + } + + while ((conn_ent = ncp_get_conn_ent(mtab)) != NULL) + { + if (spec != NULL) + { + if ( (conn_ent->uid != spec->uid) + || ( (strlen(spec->server) != 0) + && (strcasecmp(conn_ent->server, + spec->server) != 0)) + || ( (strlen(spec->user) != 0) + && (strcasecmp(conn_ent->user, + spec->user) != 0))) + { + continue; + } + } + + mount_fid = open(conn_ent->mount_point, O_RDONLY, 0); + if (mount_fid < 0) + { + continue; + } + + i.version = NCP_GET_FS_INFO_VERSION; + + if (ioctl(mount_fid, NCP_IOC_GET_FS_INFO, &i) < 0) + { + close(mount_fid); + continue; + } + + close(mount_fid); + result = conn_ent->mount_point; + break; + } + + fclose(mtab); + errno = (result == NULL) ? ENOENT : 0; + return result; +} + +static int +ncp_open_permanent(struct ncp_conn *conn, + const struct ncp_conn_spec *spec) +{ + char *mount_point; + + if (conn->is_connected != NOT_CONNECTED) + { + errno = EBUSY; + return -1; + } + + if ((mount_point = ncp_find_permanent(spec)) == NULL) + { + return -1; + } + + if (strlen(mount_point) >= sizeof(conn->mount_point)) + { + errno = ENAMETOOLONG; + return -1; + } + + /* The rest has already been done in ncp_find_permanent, so we + * do not check errors anymore */ + conn->mount_fid = open(mount_point, O_RDONLY, 0); + conn->i.version = NCP_GET_FS_INFO_VERSION; + ioctl(conn->mount_fid, NCP_IOC_GET_FS_INFO, &(conn->i)); + if (spec != NULL) + { + strncpy(conn->server, spec->server, sizeof(conn->server)); + strncpy(conn->user, spec->user, sizeof(conn->user)); + } + else + { + memset(conn->server, '\0', sizeof(conn->server)); + memset(conn->user, '\0', sizeof(conn->user)); + } + strcpy(conn->mount_point, mount_point); + conn->is_connected = CONN_PERMANENT; + return 0; +} + +struct ncp_conn * +ncp_open(struct ncp_conn_spec *spec, long *err) +{ + struct ncp_conn *result; + + initialize_NCPL_error_table(); + + result = malloc(sizeof(struct ncp_conn)); + + if (result == NULL) + { + *err = ENOMEM; + return NULL; + } + + memzero(*result); + + if (ncp_open_permanent(result, spec) == 0) + { + return result; + } + + if ((*err = ncp_open_temporary(result, spec)) != 0) + { + free(result); + return NULL; + } + return result; +} + + +struct ncp_conn * +ncp_open_mount(const char *mount_point, long *err) +{ + struct ncp_conn *result; + + initialize_NCPL_error_table(); + + if (strlen(mount_point) >= sizeof(result->mount_point)) + { + *err = ENAMETOOLONG; + return NULL; + } + + result = malloc(sizeof(struct ncp_conn)); + + if (result == NULL) + { + *err = ENOMEM; + return NULL; + } + + memzero(*result); + + result->is_connected = NOT_CONNECTED; + + result->mount_fid = open(mount_point, O_RDONLY, 0); + if (result->mount_fid < 0) + { + free(result); + *err = ENODEV; + return NULL; + } + strcpy(result->mount_point, mount_point); + result->is_connected = CONN_PERMANENT; + + result->i.version = NCP_GET_FS_INFO_VERSION; + + if (ioctl(result->mount_fid, NCP_IOC_GET_FS_INFO, &(result->i)) != 0) + { + free(result); + *err = NCPL_ET_NO_NCPFS_FILE; + return NULL; + } + return result; +} + +static long +ncp_user_disconnect(struct ncp_conn *conn) +{ + struct ncp_request_header *h + = (struct ncp_request_header *)(conn->packet); + long result; + + h->type = NCP_DEALLOC_SLOT_REQUEST; + + conn->sequence += 1; + h->sequence = conn->sequence; + h->conn_low = (conn->i.connection) & 0xff; + h->conn_high = ((conn->i.connection) & 0xff00) >> 8; + h->task = 1; + h->function = 0; + + if ((result = do_ncp_call(conn, sizeof(*h))) != 0) + { + return result; + } + + close(conn->ncp_sock); + close(conn->wdog_sock); + + if (conn->wdog_pid != 0) + { + kill(conn->wdog_pid, SIGTERM); + wait(NULL); + } + + return 0; +} + +static long +ncp_do_close(struct ncp_conn *conn) +{ + long result = -1; + + switch (conn->is_connected) + { + case CONN_PERMANENT: + result = close(conn->mount_fid); + break; + + case CONN_TEMPORARY: + result = ncp_user_disconnect(conn); + break; + + default: + break; + } + + conn->is_connected = NOT_CONNECTED; + + return result; +} + +long +ncp_close(struct ncp_conn *conn) +{ + long result; + if (conn == NULL) + { + return 0; + } + + if ((result = ncp_do_close(conn)) != 0) + { + return result; + } + free(conn); + return 0; +} + +struct ncp_conn_ent * +ncp_get_conn_ent(FILE *filep) +{ + static struct ncp_conn_ent entry; + char server[2*NCP_BINDERY_NAME_LEN]; + char *user; + struct mntent *mnt_ent; + int fid; + + memzero(server); + memzero(entry); + + while ((mnt_ent = getmntent(filep)) != NULL) + { + if (strcmp(mnt_ent->mnt_type, "ncpfs") != 0) + { + continue; + } + + if (strlen(mnt_ent->mnt_fsname) >= sizeof(server)) + { + continue; + } + + strcpy(server, mnt_ent->mnt_fsname); + user = strchr(server, '/'); + if (user != NULL) + { + *user = '\0'; + user += 1; + if (strlen(user) >= sizeof(entry.user)) + { + continue; + } + strcpy(entry.user, user); + } + + if ( (strlen(server) >= sizeof(entry.server)) + || (strlen(mnt_ent->mnt_dir) >= sizeof(entry.mount_point))) + { + continue; + } + strcpy(entry.server, server); + strcpy(entry.mount_point, mnt_ent->mnt_dir); + + fid = open(entry.mount_point, O_RDONLY, 0); + + if (fid == -1) + { + continue; + } + + if (ioctl(fid, NCP_IOC_GETMOUNTUID, &entry.uid) != 0) { + close(fid); + continue; + } + + close(fid); + return &entry; + } + + return NULL; +} + +static struct ncp_conn_spec * +ncp_get_nwc_ent(FILE *nwc) +{ + static struct ncp_conn_spec spec; + char line[512]; + int line_len; + char *user; + char *password; + + memzero(spec); + spec.uid = getuid(); + + while (fgets(line, sizeof(line), nwc) != NULL) + { + if ( (line[0] == '\n') + || (line[0] == '#')) + { + continue; + } + + line_len = strlen(line); + if (line[line_len-1] == '\n') + { + line[line_len-1] = '\0'; + } + + user = strchr(line, '/'); + password = strchr(user != NULL ? user : line, ' '); + + if (password != NULL) + { + *password = '\0'; + password += 1; + } + + if (user != NULL) + { + *user = '\0'; + user += 1; + if (strlen(user) >= sizeof(spec.user)) + { + continue; + } + strcpy(spec.user, user); + } + + if (strlen(line) >= sizeof(spec.server)) + { + continue; + } + strcpy(spec.server, line); + + if (password != NULL) + { + while (*password == ' ') + { + password += 1; + } + + if (strlen(password) >= sizeof(spec.password)) + { + continue; + } + strcpy(spec.password, password); + } + return &spec; + } + return NULL; +} + +FILE * +ncp_fopen_nwc(const char *user, const char *mode, long *err) +{ + char path[MAXPATHLEN]; + char *home = NULL; + struct stat st; + + if (mode == NULL) + { + mode = "r"; + } + + if (user == NULL) + { + home = getenv("HOME"); + } + else + { + struct passwd *pwd; + + if ((pwd = getpwnam(user)) != NULL) + { + home = pwd->pw_dir; + } + } + + if ( (home == NULL) + || (strlen(home) + sizeof(NWCLIENT) + 2 > sizeof(path))) + { + *err = ENAMETOOLONG; + return NULL; + } + + strcpy(path, home); + strcat(path, "/"); + strcat(path, NWCLIENT); + + if (stat(path, &st) != 0) + { + *err = errno; + return NULL; + } + + if ((st.st_mode & (S_IRWXO | S_IRWXG)) != 0) + { + *err = NCPL_ET_INVALID_MODE; + return NULL; + } + + return fopen(path, mode); +} + +struct ncp_conn_spec * +ncp_find_conn_spec(const char *server, const char *user, const char *password, + int login_necessary, uid_t uid, long *err) +{ + static struct ncp_conn_spec spec; + + struct ncp_conn conn; + + FILE *nwc; + struct ncp_conn_spec *nwc_ent; + + initialize_NCPL_error_table(); + + *err = 0; + memzero(spec); + spec.uid = getuid(); + + if (server != NULL) + { + if (strlen(server) >= sizeof(spec.server)) + { + *err = NCPL_ET_NAMETOOLONG; + return NULL; + } + strcpy(spec.server, server); + } + else + { + if ((nwc = ncp_fopen_nwc(NULL, NULL, err)) == NULL) + { + *err = NCPL_ET_NO_SERVER; + return NULL; + } + + nwc_ent = ncp_get_nwc_ent(nwc); + fclose(nwc); + + if (nwc_ent == NULL) + { + *err = NCPL_ET_NO_SPEC; + return NULL; + } + strcpy(spec.server, nwc_ent->server); + strcpy(spec.user, nwc_ent->user); + } + + str_upper(spec.server); + + if (login_necessary == 0) + { + memset(spec.user, 0, sizeof(spec.user)); + memset(spec.password, 0, sizeof(spec.password)); + return &spec; + } + + if (user != NULL) + { + if (strlen(user) >= sizeof(spec.user)) + { + *err = NCPL_ET_NAMETOOLONG; + return NULL; + } + strcpy(spec.user, user); + } + + str_upper(spec.user); + spec.login_type = NCP_BINDERY_USER; + + if (ncp_open_permanent(&conn, &spec) == 0) + { + ncp_do_close(&conn); + return &spec; + } + + if (password != NULL) + { + if (strlen(password) >= sizeof(spec.password)) + { + *err = NCPL_ET_NAMETOOLONG; + return NULL; + } + strcpy(spec.password, password); + } + else + { + if ((nwc = ncp_fopen_nwc(NULL, NULL, err)) != NULL) + { + while ((nwc_ent = ncp_get_nwc_ent(nwc)) != NULL) + { + if ( (strcasecmp(spec.server, + nwc_ent->server) != 0) + || ( (*spec.user != '\0') + && (strcasecmp(spec.user, + nwc_ent->user) != 0))) + { + continue; + } + strcpy(spec.user, nwc_ent->user); + strcpy(spec.password, nwc_ent->password); + break; + } + fclose(nwc); + } + } + + if (strlen(spec.user) == 0) + { + *err = NCPL_ET_NO_USER; + return NULL; + } + + if ((strlen(spec.password) == 0) && (password == NULL)) + { + char *password; + if (!(isatty(0) && isatty(1))) + { + return NULL; + } + printf("Logging into %s as %s\n", + spec.server, spec.user); + + password = getpass("Password: "); + if (strlen(password) > sizeof(spec.password)) + { + return NULL; + } + strcpy(spec.password, password); + } + else + { + if (strcmp(spec.password, NWC_NOPASSWORD) == 0) + { + *spec.password = '\0'; + } + } + + str_upper(spec.server); + str_upper(spec.user); + str_upper(spec.password); + return &spec; +} + +struct ncp_conn * +ncp_initialize_as(int *argc, char **argv, + int login_necessary, int login_type, long *err) +{ + char *server = NULL; + char *user = NULL; + char *password = NULL; + struct ncp_conn_spec *spec; + int i = 1; + + int get_argument(int arg_no, char **target) + { + int count = 1; + + if (target != NULL) + { + if (arg_no+1 >= *argc) + { + /* No argument to switch */ + errno = EINVAL; + return -1; + } + *target = argv[arg_no+1]; + count = 2; + } + + /* Delete the consumed switch from the argument list + and decrement the argument count */ + while (count+arg_no < *argc) + { + argv[arg_no] = argv[arg_no+count]; + arg_no += 1; + } + *argc -= count; + return 0; + } + + initialize_NCPL_error_table(); + + *err = EINVAL; + + while (i < *argc) + { + if ( (argv[i][0] != '-') + || (strlen(argv[i]) != 2)) + { + i += 1; + continue; + } + + switch (argv[i][1]) + { + case 'S': + if (get_argument(i, &server) != 0) + { + return NULL; + } + continue; + case 'U': + if (get_argument(i, &user) != 0) + { + return NULL; + } + continue; + case 'P': + if (get_argument(i, &password) != 0) + { + return NULL; + } + continue; + case 'n': + if (get_argument(i, 0) != 0) + { + return NULL; + } + password = NWC_NOPASSWORD; + continue; + } + i += 1; + } + + spec = ncp_find_conn_spec(server, user, password, login_necessary, + getuid(), err); + + if (spec == NULL) + { + if (login_necessary != 0) + { + return NULL; + } + else + { + return ncp_open(NULL, err); + } + } + + spec->login_type = login_type; + + if (login_necessary == 0) + { + spec->user[0] = '\0'; + } + + return ncp_open(spec, err); +} + +struct ncp_conn * +ncp_initialize(int *argc, char **argv, + int login_necessary, long *err) +{ + return ncp_initialize_as(argc, argv, login_necessary, + NCP_BINDERY_USER, err); +} + +static long +ncp_request(struct ncp_conn *conn, int function) +{ + switch (conn->is_connected) { + case CONN_PERMANENT: + return ncp_mount_request(conn, function); + case CONN_TEMPORARY: + return ncp_temp_request(conn, function); + default: + } + return ENOTCONN; +} + +/****************************************************************************/ +/* */ +/* Helper functions */ +/* */ +/****************************************************************************/ + +static inline int +min(int a, int b) +{ + return (alock == 0) { + ncp_printf("ncpfs: conn not locked!\n"); + } +} + +static void +ncp_add_byte(struct ncp_conn *conn, byte x) +{ + assert_conn_locked(conn); + *(byte *)(&(conn->packet[conn->current_size])) = x; + conn->current_size += 1; + return; +} + +static void +ncp_add_word(struct ncp_conn *conn, word x) +{ + assert_conn_locked(conn); + *(word *)(&(conn->packet[conn->current_size])) = x; + conn->current_size += 2; + return; +} + +static void +ncp_add_mem(struct ncp_conn *conn, const void *source, int size) +{ + assert_conn_locked(conn); + memcpy(&(conn->packet[conn->current_size]), source, size); + conn->current_size += size; + return; +} + +static void +ncp_add_pstring(struct ncp_conn *conn, const char *s) +{ + int len = strlen(s); + assert_conn_locked(conn); + if (len > 255) { + ncp_printf("ncpfs: string too long: %s\n", s); + len = 255; + } + ncp_add_byte(conn, len); + ncp_add_mem(conn, s, len); + return; +} + +static void +ncp_init_request(struct ncp_conn *conn) +{ + ncp_lock_conn(conn); + + conn->current_size = sizeof(struct ncp_request_header); + conn->has_subfunction = 0; +} + +static void +ncp_init_request_s(struct ncp_conn *conn, int subfunction) +{ + ncp_init_request(conn); + ncp_add_word(conn, 0); /* preliminary size */ + + ncp_add_byte(conn, subfunction); + + conn->has_subfunction = 1; +} + +static char * +ncp_reply_data(struct ncp_conn *conn, int offset) +{ + return &(conn->packet[sizeof(struct ncp_reply_header) + offset]); +} + +static byte +ncp_reply_byte(struct ncp_conn *conn, int offset) +{ + return *(byte *)(ncp_reply_data(conn, offset)); +} + +static word +ncp_reply_word(struct ncp_conn *conn, int offset) +{ + return *(word *)(ncp_reply_data(conn, offset)); +} + +static dword +ncp_reply_dword(struct ncp_conn *conn, int offset) +{ + return *(dword *)(ncp_reply_data(conn, offset)); +} + +/* Here the ncp calls begin + */ + +static long +ncp_negotiate_buffersize(struct ncp_conn *conn, + int size, int *target) +{ + long result; + + ncp_init_request(conn); + ncp_add_word(conn, htons(size)); + + if ((result = ncp_request(conn, 33)) != 0) { + ncp_unlock_conn(conn); + return result; + } + + *target =min(ntohs(ncp_reply_word(conn, 0)), size); + + ncp_unlock_conn(conn); + return 0; +} + +/* + * target is a 8-byte buffer + */ +long +ncp_get_encryption_key(struct ncp_conn *conn, + char *target) +{ + long result; + + ncp_init_request_s(conn, 23); + + if ((result = ncp_request(conn, 23)) != 0) { + ncp_unlock_conn(conn); + return result; + } + + if (conn->ncp_reply_size < 8) { + ncp_printf("ncp_reply_size %d < 8\n", + conn->ncp_reply_size); + ncp_unlock_conn(conn); + return result; + } + + memcpy(target, ncp_reply_data(conn, 0), 8); + ncp_unlock_conn(conn); + return 0; +} + +long +ncp_get_bindery_object_id(struct ncp_conn *conn, + __u16 object_type, + const char *object_name, + struct ncp_bindery_object *target) +{ + long result; + ncp_init_request_s(conn, 53); + ncp_add_word(conn, htons(object_type)); + ncp_add_pstring(conn, object_name); + + if ((result = ncp_request(conn, 23)) != 0) { + ncp_unlock_conn(conn); + return result; + } + + if (conn->ncp_reply_size < 54) { + ncp_printf("ncp_reply_size %d < 54\n", + conn->ncp_reply_size); + ncp_unlock_conn(conn); + return result; + } + + target->object_id = ntohl(ncp_reply_dword(conn, 0)); + target->object_type = ntohs(ncp_reply_word (conn, 4)); + memcpy(target->object_name, ncp_reply_data(conn, 6), 48); + ncp_unlock_conn(conn); + return 0; +} + +long +ncp_read_property_value(struct ncp_conn *conn, + int object_type, const char *object_name, + int segment, const char *prop_name, + struct nw_property *target) +{ + long result; + ncp_init_request_s(conn, 61); + ncp_add_word(conn, htons(object_type)); + ncp_add_pstring(conn, object_name); + ncp_add_byte(conn, segment); + ncp_add_pstring(conn, prop_name); + + if ((result = ncp_request(conn, 23)) != 0) { + ncp_unlock_conn(conn); + return result; + } + + memcpy(&(target->value), ncp_reply_data(conn, 0), 128); + target->more_flag = ncp_reply_byte(conn, 128); + target->property_flag = ncp_reply_byte(conn, 129); + ncp_unlock_conn(conn); + return 0; +} + +long +ncp_login_encrypted(struct ncp_conn *conn, + const struct ncp_bindery_object *object, + const unsigned char *key, + const unsigned char *passwd) +{ + dword tmpID = htonl(object->object_id); + unsigned char buf[128]; + unsigned char encrypted[8]; + long result; + + shuffle((byte *)&tmpID, passwd, strlen(passwd), buf); + nw_encrypt(key, buf, encrypted); + + ncp_init_request_s(conn, 24); + ncp_add_mem(conn, encrypted, 8); + ncp_add_word(conn, htons(object->object_type)); + ncp_add_pstring(conn, object->object_name); + + result = ncp_request(conn, 23); + ncp_unlock_conn(conn); + return result; +} + +long +ncp_login_unencrypted(struct ncp_conn *conn, + __u16 object_type, const char *object_name, + const unsigned char *passwd) +{ + long result; + ncp_init_request_s(conn, 20); + ncp_add_word(conn, htons(object_type)); + ncp_add_pstring(conn, object_name); + ncp_add_pstring(conn, passwd); + result = ncp_request(conn, 23); + ncp_unlock_conn(conn); + return result; +} + +long +ncp_login_user(struct ncp_conn *conn, + const unsigned char *username, + const unsigned char *password) +{ + return ncp_login_object(conn, username, NCP_BINDERY_USER, password); +} + +static long +ncp_login_object(struct ncp_conn *conn, + const unsigned char *username, + int login_type, + const unsigned char *password) +{ + long result; + unsigned char ncp_key[8]; + struct ncp_bindery_object user; + + if ((result = ncp_get_encryption_key(conn, ncp_key)) != 0) { + return ncp_login_unencrypted(conn, login_type, username, + password); + } + + if ((result = ncp_get_bindery_object_id(conn, login_type, + username, &user)) != 0) { + return result; + } + + if ((result = ncp_login_encrypted(conn, &user, + ncp_key, password)) != 0) + { + struct nw_property p; + struct ncp_prop_login_control *l + = (struct ncp_prop_login_control *)&p; + + if (conn->completion != NCP_GRACE_PERIOD) + { + return result; + } + + fprintf(stderr, "Your password has expired\n"); + + if ((result = ncp_read_property_value(conn, NCP_BINDERY_USER, + username, 1, + "LOGIN_CONTROL", + &p)) == 0) + { + fprintf(stderr, "You have %d login attempts left\n", + l->GraceLogins); + } + } + return 0; +} diff --git a/sutil/ncplib.h b/sutil/ncplib.h new file mode 100644 index 0000000..7aaaf44 --- /dev/null +++ b/sutil/ncplib.h @@ -0,0 +1,198 @@ +/* + * ncplib.h + * + * Copyright (C) 1995, 1996 by Volker Lendecke + * + */ + +#ifndef _NCPLIB_H +#define _NCPLIB_H + +#include +#include +#include +#include +#include +#include +#include + +#include "ipxlib.h" +#include "com_err.h" + +#ifndef memzero +#include +#define memzero(object) memset(&(object), 0, sizeof(object)) +#endif + +void +str_upper(char *name); + +enum connect_state { + NOT_CONNECTED = 0, + CONN_PERMANENT, + CONN_TEMPORARY +}; + +struct ncp_conn { + + enum connect_state is_connected; + + char server[NCP_BINDERY_NAME_LEN]; + char user [NCP_BINDERY_NAME_LEN]; + + struct ncp_fs_info i; + + /* Fields for use with permanent connections */ + int mount_fid; + char mount_point[MAXPATHLEN]; + + /* Fields for use with temporary connections */ + int ncp_sock; + int wdog_sock; + int wdog_pid; + __u8 sequence; + int completion; + int conn_status; + int reply_size; + + /* Fields used to setup ncp requests */ + int current_size; + int has_subfunction; + int verbose; + int ncp_reply_size; + + int lock; + + char packet[NCP_PACKET_SIZE]; +}; + +struct ncp_conn_spec { + char server[NCP_BINDERY_NAME_LEN]; + char user[NCP_BINDERY_NAME_LEN]; + uid_t uid; + int login_type; /* NCP_BINDERY_USER / NCP_BINDERY_PSERVER */ + char password[NCP_BINDERY_NAME_LEN]; +}; + +struct ncp_property_info { + __u8 property_name[16]; + __u8 property_flags; + __u8 property_security; + __u32 search_instance; + __u8 value_available_flag; + __u8 more_properties_flag; +}; + +/* ncp_initialize is the main entry point for user programs which want + to connect to a NetWare Server. It looks for -S, -U, -P and -n in + the argument list, opens the connection and removes the arguments + from the list. It was designed after the X Windows init + functions. */ +struct ncp_conn * +ncp_initialize(int *argc, char **argv, + int login_necessary, long *err); + +/* You can login as another object by this procedure. As a first use + pserver comes to mind. */ +struct ncp_conn * +ncp_initialize_as(int *argc, char **argv, + int login_necessary, int login_type, long *err); + + +/* Open a connection */ +struct ncp_conn * +ncp_open(struct ncp_conn_spec *spec, long *err); + +/* Open a connection on an existing mount point */ +struct ncp_conn * +ncp_open_mount(const char *mount_point, long *err); + +/* Find a permanent connection that fits the spec, return NULL if + * there is none. */ +char * +ncp_find_permanent(const struct ncp_conn_spec *spec); + +/* Find the address of a file server */ +struct sockaddr_ipx * +ncp_find_fileserver(char *server_name, long *err); + +/* Find the address of a server */ +struct sockaddr_ipx * +ncp_find_server(char **server_name, int type, long *err); + +/* Detach from a permanent connection or destroy a temporary + connection */ +long +ncp_close(struct ncp_conn *conn); + +/* like getmntent, get_ncp_conn_ent scans /etc/mtab for usable + connections */ + +struct ncp_conn_ent { + char server[NCP_BINDERY_NAME_LEN]; + char user[NCP_BINDERY_NAME_LEN]; + uid_t uid; + char mount_point[MAXPATHLEN]; +}; + +struct ncp_conn_ent * +ncp_get_conn_ent(FILE *filep); + +#define NWCLIENT (".nwclient") +#define NWC_NOPASSWORD ("-") + +/* find an appropriate connection */ + +struct ncp_conn_spec * +ncp_find_conn_spec(const char *server, const char *user, const char *password, + int login_necessary, uid_t uid, long *err); + +long +ncp_get_encryption_key(struct ncp_conn *conn, + char *target); + +struct ncp_station_addr { + __u32 NetWork __attribute__ ((packed)); + __u8 Node[6] __attribute__ ((packed)); + __u16 Socket __attribute__ ((packed)); +}; + +struct ncp_prop_login_control { + __u8 AccountExpireDate[3] __attribute__ ((packed)); + __u8 Disabled __attribute__ ((packed)); + __u8 PasswordExpireDate[3] __attribute__ ((packed)); + __u8 GraceLogins __attribute__ ((packed)); + __u16 PasswordExpireInterval __attribute__ ((packed)); + __u8 MaxGraceLogins __attribute__ ((packed)); + __u8 MinPasswordLength __attribute__ ((packed)); + __u16 MaxConnections __attribute__ ((packed)); + __u8 ConnectionTimeMask[42] __attribute__ ((packed)); + __u8 LastLogin[6] __attribute__ ((packed)); + __u8 RestrictionMask __attribute__ ((packed)); + __u8 reserved __attribute__ ((packed)); + __u32 MaxDiskUsage __attribute__ ((packed)); + __u16 BadLoginCount __attribute__ ((packed)); + __u32 BadLoginCountDown __attribute__ ((packed)); + struct ncp_station_addr LastIntruder __attribute__ ((packed)); +}; + +long +ncp_read_property_value(struct ncp_conn *conn, + int object_type, const char *object_name, + int segment, const char *prop_name, + struct nw_property *target); + +#define NCP_GRACE_PERIOD (0xdf) + +long +ncp_get_bindery_object_id(struct ncp_conn *conn, + __u16 object_type, + const char *object_name, + struct ncp_bindery_object *target); + +long +ncp_login_user(struct ncp_conn *conn, + const unsigned char *username, + const unsigned char *password); + +#endif /* _NCPLIB_H */ diff --git a/util/ncpmount.c b/sutil/ncpmount.c similarity index 100% rename from util/ncpmount.c rename to sutil/ncpmount.c diff --git a/util/ncpumount.c b/sutil/ncpumount.c similarity index 95% rename from util/ncpumount.c rename to sutil/ncpumount.c index 2c72bf5..521776e 100644 --- a/util/ncpumount.c +++ b/sutil/ncpumount.c @@ -86,6 +86,11 @@ canonicalize (const char *path) if (realpath (path, canonical)) return canonical; + if (strlen(path) > PATH_MAX) + { + return NULL; + } + strcpy (canonical, path); return canonical; } @@ -116,7 +121,15 @@ main(int argc, char *argv[]) mount_point = canonicalize(argv[1]); + if (mount_point == NULL) + { + fprintf(stderr, "Invalid mount point: %s\n", argv[1]); + exit(1); + } + if (umount_ok(mount_point) != 0) { + fprintf(stderr, "You are not allowed to umount %s\n", + mount_point); exit(1); } diff --git a/sutil/nwcrypt.c b/sutil/nwcrypt.c new file mode 100644 index 0000000..4c028da --- /dev/null +++ b/sutil/nwcrypt.c @@ -0,0 +1,209 @@ +/*$********************************************************* +$* +$* This code has been taken from DDJ 11/93, from an +$* article by Pawel Szczerbina. +$* +$* Password encryption routines follow. +$* Converted to C from Barry Nance's Pascal +$* prog published in the March -93 issue of Byte. +$* +$* Adapted to be useable for ncpfs by +$* Volker Lendecke in +$* October 1995. +$* +$**********************************************************/ + +/**************************************************************************** + +I read that Novell is not very open when it comes to technical details +of the Netware Core Protocol. This might be especially true for the +encryption stuff. I took the necessary code from Dr. Dobb's Journal +11/93, Undocumented Corner. I asked Jon Erickson about +the legal status of this piece of code: + + +--- +Date: Thu, 12 Oct 1995 13:44:18 +0100 +From: Volker Lendecke +To: jon@ddj.com +Subject: legal status of your source code? + + +Hello! + +I hope that you're the right one to write to, you are the first on your WWW +server. If you are not, could you please forward this message to the right +person? Thanks. + +I'm currently exploring the possibility to write a free (in the GNU GPL +sense) NCP filesystem, which would allow me to access a novell server +transparently. For that I would like to use the encryption functions you +published in DDJ 11/93, Undocumented Corner. I would make some cosmetic +changes, such as other indentations, minor code changes and so on. But I do +not know if that allows me to publish this code under GPL. One alternative +would be to publish a diff against your listing, but that would probably +contain much of your code as well, and it would be very inconvenient for +the average user. + +I think that you have some kind of standard procedure for such a +case. Please tell me what I should do. + +Many thanks in advance, + + Volker + + +=================================================================+ + ! Volker Lendecke Internet: lendecke@namu01.gwdg.de ! + ! D-37081 Goettingen, Germany ! + +=================================================================+ + +-- + + +I got the following answer: + +--- +From: Jon Erickson +X-Mailer: SCO System V Mail (version 3.2) +To: lendecke@namu01.gwdg.de +Subject: Re: legal status of your source code? +Date: Thu, 12 Oct 95 5:42:56 PDT + +Volker, +Code from Dr. Dobb's Journal related articles is provided for +anyone to use. Clearly, the author of the article should be +given credit. +Jon Erickson + +--- + +With this answer in mind, I took the code and made it a bit more +C-like. The original seemed to be translated by a mechanical pascal->c +translator. Jon's answer encouraged me to publish nwcrypt.c under the +GPL. If anybody who knows more about copyright and sees any problems +with this, please tell me. +****************************************************************************/ + +/******************* Data types ***************************/ +typedef unsigned char buf32[32]; +typedef unsigned char buf16[16]; +typedef unsigned char buf8[8]; +typedef unsigned char buf4[4]; + +static unsigned char encrypttable[256] = +{0x7,0x8,0x0,0x8,0x6,0x4,0xE,0x4,0x5,0xC,0x1,0x7,0xB,0xF,0xA,0x8, + 0xF,0x8,0xC,0xC,0x9,0x4,0x1,0xE,0x4,0x6,0x2,0x4,0x0,0xA,0xB,0x9, + 0x2,0xF,0xB,0x1,0xD,0x2,0x1,0x9,0x5,0xE,0x7,0x0,0x0,0x2,0x6,0x6, + 0x0,0x7,0x3,0x8,0x2,0x9,0x3,0xF,0x7,0xF,0xC,0xF,0x6,0x4,0xA,0x0, + 0x2,0x3,0xA,0xB,0xD,0x8,0x3,0xA,0x1,0x7,0xC,0xF,0x1,0x8,0x9,0xD, + 0x9,0x1,0x9,0x4,0xE,0x4,0xC,0x5,0x5,0xC,0x8,0xB,0x2,0x3,0x9,0xE, + 0x7,0x7,0x6,0x9,0xE,0xF,0xC,0x8,0xD,0x1,0xA,0x6,0xE,0xD,0x0,0x7, + 0x7,0xA,0x0,0x1,0xF,0x5,0x4,0xB,0x7,0xB,0xE,0xC,0x9,0x5,0xD,0x1, + 0xB,0xD,0x1,0x3,0x5,0xD,0xE,0x6,0x3,0x0,0xB,0xB,0xF,0x3,0x6,0x4, + 0x9,0xD,0xA,0x3,0x1,0x4,0x9,0x4,0x8,0x3,0xB,0xE,0x5,0x0,0x5,0x2, + 0xC,0xB,0xD,0x5,0xD,0x5,0xD,0x2,0xD,0x9,0xA,0xC,0xA,0x0,0xB,0x3, + 0x5,0x3,0x6,0x9,0x5,0x1,0xE,0xE,0x0,0xE,0x8,0x2,0xD,0x2,0x2,0x0, + 0x4,0xF,0x8,0x5,0x9,0x6,0x8,0x6,0xB,0xA,0xB,0xF,0x0,0x7,0x2,0x8, + 0xC,0x7,0x3,0xA,0x1,0x4,0x2,0x5,0xF,0x7,0xA,0xC,0xE,0x5,0x9,0x3, + 0xE,0x7,0x1,0x2,0xE,0x1,0xF,0x4,0xA,0x6,0xC,0x6,0xF,0x4,0x3,0x0, + 0xC,0x0,0x3,0x6,0xF,0x8,0x7,0xB,0x2,0xD,0xC,0x6,0xA,0xA,0x8,0xD}; + +static buf32 encryptkeys = +{0x48,0x93,0x46,0x67,0x98,0x3D,0xE6,0x8D, + 0xB7,0x10,0x7A,0x26,0x5A,0xB9,0xB1,0x35, + 0x6B,0x0F,0xD5,0x70,0xAE,0xFB,0xAD,0x11, + 0xF4,0x47,0xDC,0xA7,0xEC,0xCF,0x50,0xC0}; + + +static void +shuffle1(buf32 temp, unsigned char *target) +{ + short b4; + unsigned char b3; + int s, b2, i; + + b4 = 0; + + for (b2 = 0; b2 <= 1; ++b2) + { + for (s = 0; s <= 31; ++s) + { + b3 = (temp[s]+b4) ^ (temp[(s+b4)&31] - encryptkeys[s]); + b4 = b4 + b3; + temp[s] = b3; + } + } + + for (i = 0; i <= 15; ++i) { + target[i] = encrypttable[temp[ 2*i ]] + | (encrypttable[temp[ 2*i + 1]] << 4); + } +} + + +static void +shuffle(const unsigned char *lon, const unsigned char *buf, int buflen, + unsigned char *target) +{ + int b2, d, s; + buf32 temp; + + while ( (buflen > 0) + && (buf[buflen - 1] == 0)) { + buflen = buflen - 1; + } + + for (s = 0; s < 32; s++) { + temp[s] = 0; + } + + d = 0; + while (buflen >= 32) + { + for (s = 0; s <= 31; ++s) + { + temp[s] = temp[s] ^ buf[d]; + d = d + 1; + } + buflen = buflen - 32; + } + b2 = d; + if (buflen > 0) + { + for (s = 0; s <= 31; ++s) + { + if (d + buflen == b2) + { + b2 = d; + temp[s] = temp[s] ^ encryptkeys[s]; + } else { + temp[s] = temp[s] ^ buf[b2]; + b2 = b2 + 1; + } + } + } + + for (s = 0; s <= 31; ++s) + temp[s] = temp[s] ^ lon[s & 3]; + + shuffle1(temp,target); +} + + +static void +nw_encrypt(const unsigned char *fra, + const unsigned char *buf, + unsigned char *til) +{ + buf32 k; + int s; + + shuffle(&(fra[0]), buf, 16, &(k[ 0])); + shuffle(&(fra[4]), buf, 16, &(k[16])); + + for (s = 0; s <= 15; ++s) + k[s] = k[s] ^ k[31 - s]; + + for (s = 0; s <= 7; ++s) + til[s] = k[s] ^ k[15 - s]; +} diff --git a/sutil/nwsfind.c b/sutil/nwsfind.c new file mode 100644 index 0000000..2220337 --- /dev/null +++ b/sutil/nwsfind.c @@ -0,0 +1,102 @@ +/* + * nwsfind.c + * + * Find a NetWare server and open a route to it. + * This tool can safely be setuid root, if normal users should be able to + * access any NetWare server. + * + * Copyright (C) 1996 by Volker Lendecke + * + */ + +#include "ncplib.h" +#include +#include +#include + +static char *progname; + +static void +usage(void) +{ + fprintf(stderr, "usage: %s [server]\n", progname); +} + +static void +help(void) +{ + printf("\n"); + printf("usage: %s [server]\n", progname); + printf("\n" + "-t Server type, default: File server\n" + "-h Print this help text\n" + "\n"); +} + +static void +swallow_error(const char * name, long code, const char *format, va_list arg) +{ + printf("%s ", error_message(code)); + vfprintf(stdout, format, arg); + putchar('\n'); + return; +} + +int +main(int argc, char *argv[]) +{ + char *server = NULL; + int object_type = NCP_BINDERY_FSERVER; + struct sockaddr_ipx *result; + long err; + + int opt; + + progname = argv[0]; + + set_com_err_hook(swallow_error); + + while ((opt = getopt(argc, argv, "t:")) != EOF) + { + switch(opt) { + case 't': + object_type = atoi(optarg); + break; + case 'h': + case '?': + help(); + exit(1); + default: + usage(); + exit(1); + } + } + + if (optind < argc-1) + { + usage(); + exit(1); + } + + if (optind == argc-1) + { + server = argv[optind]; + if (strlen(server) >= NCP_BINDERY_NAME_LEN) + { + com_err(argv[0], ENAMETOOLONG, "server name too long"); + exit(1); + } + } + + result = ncp_find_server(&server, object_type, &err); + + if (result == NULL) + { + com_err(argv[0], err, "when trying to find server"); + exit(1); + } + + ipx_print_saddr(result); + printf(" %s\n", server); + return 0; +} diff --git a/util/Makefile b/util/Makefile index 1b02dec..0a9e77b 100644 --- a/util/Makefile +++ b/util/Makefile @@ -5,30 +5,18 @@ USERUTILS = slist pqlist nwfsinfo pserver nprint nsend ncopy nwpasswd USERUTILS += nwbols nwbocreate nwborm nwboprops USERUTILS += nwbpcreate nwbprm nwbpvalues nwbpadd nwbpset -USERUTILS += nwgrant nwrevoke nwuserlist nwrights -UIDUTILS = ncpmount ncpumount +USERUTILS += nwgrant nwrevoke nwuserlist nwrights nwauth SBINUTILS = nwmsg -UTIL_EXECS = $(USERUTILS) $(UIDUTILS) $(SBINUTILS) -UTILS = $(addprefix $(INTERM_BINDIR)/,$(UTIL_EXECS)) +UTILS = $(USERUTILS) $(SBINUTILS) ncptest -CFLAGS = -Wall $(INCLUDES) $(KERNELD) -DNCPFS_VERSION=\"$(VERSION)\" CC = gcc -#CFLAGS += -g -CFLAGS += -O2 - ifeq ($(HAVE_ELF),yes) -PIC_FLAG = -fPIC NCP_LIB = libncp.so.1.0 -LIB_LINK_COMMAND = gcc -shared -Wl,-soname,libncp.so.1 -o $(NCP_LIB) -INSTALL_LIB = install $(NCP_LIB) -m 755 /lib; \ - ln -sf $(NCP_LIB) /lib/libncp.so.1; \ - ldconfig -export PIC_FLAG else NCP_LIB = libncp.a -LIB_LINK_COMMAND = ar r libncp.a +LIBDEP = ../lib/libncp.a endif default: @@ -37,59 +25,22 @@ default: all: $(UTILS) ncptest install: all - for i in $(UTIL_EXECS); \ - do install $(INTERM_BINDIR)/$$i -m 755 $(BINDIR); done - for i in $(UIDUTILS); \ - do install $(INTERM_BINDIR)/$$i -m 4755 $(BINDIR); done + for i in $(USERUTILS); \ + do install $$i -m 755 $(BINDIR); done for i in $(SBINUTILS); \ - do install $(INTERM_BINDIR)/$$i -m 755 $(SBINDIR); done - $(INSTALL_LIB) + do install $$i -m 755 $(SBINDIR); done -$(UTILS): $(addsuffix .o,$(UTIL_EXECS)) $(NCP_LIB) - $(CC) -o $@ $(addsuffix .o,$(notdir $@)) -L. -lncp +$(UTILS): %: %.o $(LIBDEP) + $(CC) -o $@ $(addsuffix .o,$@) -L../lib -lncp -ncplib.o: ncplib.c ncplib.h ncplib_err.h - $(CC) $(CFLAGS) $(PIC_FLAG) -finline-functions -c ncplib.c - -COM_ERR_CFILES = com_err/com_err.c com_err/error_message.c com_err/et_name.c \ - com_err/init_et.c - -$(NCP_LIB): ncplib.o ncplib_err.o $(COM_ERR_CFILES) - make -C com_err - $(LIB_LINK_COMMAND) ncplib.o ncplib_err.o \ - com_err/com_err.o com_err/error_message.o com_err/et_name.o \ - com_err/init_et.o - ln -sf libncp.so.1.0 libncp.so.1 - ln -sf libncp.so.1 libncp.so - export LD_LIBRARY_PATH=`pwd`:$LD_LIBRARY_PATH - -ncplib_err.o: ncplib_err.h ncplib_err.c - $(CC) $(CFLAGS) $(PIC_FLAG) -c ncplib_err.c - -ncplib_err.h: ncplib_err.et - com_err/compile_et ncplib_err - -ncplib_err.c: ncplib_err.et - com_err/compile_et ncplib_err - -test: test.o ncplib.o - $(CC) -o test test.o ncplib.o - -ncptest: ncptest.o $(NCP_LIB) - $(CC) -o ncptest ncptest.o -L. -lncp - -dep: ncplib_err.h - make -C com_err dep +dep: $(CPP) -M $(INCLUDES) *.c > .depend clean: - make -C com_err clean - rm -f *.o *~ slist test ncptest ncplib_err.[ch] - rm -f libncp.* + rm -f *.o *~ $(UTILS) mrproper: clean - make -C com_err mrproper - rm -f $(UTILS) .depend $(DISTFILE) + rm -f .depend # # include a dependency file if one exists diff --git a/util/com_err.h b/util/com_err.h deleted file mode 120000 index 2f20682..0000000 --- a/util/com_err.h +++ /dev/null @@ -1 +0,0 @@ -com_err/com_err.h \ No newline at end of file diff --git a/util/nwauth.c b/util/nwauth.c new file mode 100644 index 0000000..a4946ea --- /dev/null +++ b/util/nwauth.c @@ -0,0 +1,127 @@ +/* + * nwauth.c + * + * Check a user/passwd against a NetWare server + * + * Copyright (C) 1996 by Volker Lendecke + * + */ + +#include "ncplib.h" +#include +#include +#include + +static char *progname; + +static void +usage(void) +{ + fprintf(stderr, "usage: %s [options]\n", progname); +} + +static void +help(void) +{ + printf("\n"); + printf("usage: %s [options]\n", progname); + printf("\n" + "-h Print this help text\n" + "-S server Server name to be used\n" + "-U username Username sent to server\n" + "-t type Object type (decimal value)\n" + "\n"); +} + +static void +swallow_error(const char * s, long x, const char *t, va_list arg) +{ + return; +} + +int +main(int argc, char *argv[]) +{ + struct ncp_conn_spec *spec; + struct ncp_conn *conn; + char *server = NULL; + char *object_name = NULL; + int object_type = NCP_BINDERY_USER; + long err; + + char *str; + + int opt; + + progname = argv[0]; + + if (!isatty(0)) + { + set_com_err_hook(swallow_error); + } + + while ((opt = getopt(argc, argv, "h?S:U:t:")) != EOF) + { + switch(opt) { + case 'S': + server = optarg; + break; + case 'U': + object_name = optarg; + break; + case 't': + object_type = atoi(optarg); + break; + case 'h': + case '?': + help(); + exit(1); + default: + usage(); + exit(1); + } + } + + spec = ncp_find_conn_spec(server, object_name, "", + 1, getuid(), &err); + + if (spec == NULL) + { + com_err(argv[0], err, "when trying to find server"); + exit(1); + } + + if (ncp_find_fileserver(spec->server, &err) == NULL) + { + com_err(argv[0], err, "when trying to find server"); + exit(1); + } + + spec->login_type = object_type; + memset(spec->password, 0, sizeof(spec->password)); + + if (isatty(0)) + { + str = getpass("Enter password: "); + if (strlen(str) >= sizeof(spec->password)) + { + printf("Password too long\n"); + exit(1); + } + strcpy(spec->password, str); + } + else + { + fgets(spec->password, sizeof(spec->password), stdin); + } + + str_upper(spec->password); + + if ((conn = ncp_open(spec, &err)) == NULL) + { + com_err(argv[0], err, "when trying to open connection"); + exit(1); + } + ncp_close(conn); + return 0; +} diff --git a/util/pserver.c b/util/pserver.c index a80b389..203ff38 100644 --- a/util/pserver.c +++ b/util/pserver.c @@ -260,6 +260,70 @@ init_queue(struct ncp_conn *conn, char *queue_name, char *command, } +void +build_command(struct nw_queue *q, struct queue_job *j, + char *target, int target_size) +{ + char *s = q->command; + char *target_end = target+target_size; + + void add_string(char *s) + { + int len = strlen(s); + if (target + len + 1 > target_end) + { + len = target_end - target - 1; + } + strncpy(target, s, len); + target += len; + } + + + memset(target, 0, target_size); + + while ((*s != 0) && (target < target_end)) + { + if (*s != '%') + { + *target = *s; + target += 1; + s += 1; + continue; + } + + switch (*(s+1)) + { + case '%': + *target = '%'; + target += 1; + case 'u': + { + char *user; + struct ncp_bindery_object u; + if (ncp_get_bindery_object_name + (q->conn, j->j.ClientObjectID, &u) + == 0) + { + user = u.object_name; + } + else + { + user = "*UNKNOWN USER*"; + } + add_string(user); + } + default: + *target = '%'; + *(target+1) = *(s+1); + target += 2; + } + s += 2; + } +} + + + + static int poll_queue(struct nw_queue *q) { @@ -316,6 +380,8 @@ poll_queue(struct nw_queue *q) { /* child */ + char command[2048]; + close(fd[1]); /* close write end */ if (fd[0] != STDIN_FILENO) @@ -329,7 +395,9 @@ poll_queue(struct nw_queue *q) close(fd[0]); } - execl("/bin/sh", "sh", "-c", q->command, NULL); + build_command(q, &job, command, sizeof(command)); + + execl("/bin/sh", "sh", "-c", command, NULL); syslog(LOG_ERR, "exec error: %m\n"); close(fd[0]); exit(1);