多语言展示
当前在线:1728今日阅读:155今日分享:35

如何自己创造一个软件沙箱

新年到了,伴随着新年的钟声,人们各自回到了温馨的家,绽开了可爱的笑脸。然而,在世界的某个角落,有一群人,他们在利用各个软件漏洞来榨取人们的钱财,扼杀人们对世界和平的信心!没错,就是他们!为了我们的合法权益,我们必须学会保护自己!!来吧,让我们一起用我们的知识创造一个我们的软件沙箱!!
工具/原料
1

C++语言基础

2

Windows编程基础

3

Visual Studio 2012或以上

前言

如果我们要自己创造一个“软件沙箱”,困难度极高!!如果跃升网络就更为复杂,本章只是介绍利用基础知识来创造一个具有基础功能的“软件沙箱”而已!!下面,我们先来参考一下他人的作品,来看看我们应该如何创造一个自己的沙箱。为了实现自己的“沙箱”我们可以:1.我们可以利用一个虚拟环境来运行程序!!2.但是,如果需要我们自己创造一个虚拟环境,困难度也是极高的!!好消息是:Windows作业内核对象能完成类似的“沙箱”功能!!

用户接口

首先要设计好好用户界面:为了简单,我们用一个对话框来作为“软件沙箱”的用户接口,再加上几个静态文本、Edit编辑框、Button按钮、ListBox就完成了用户界面。至于图标,对话框对图标的设置可以调用SetClassLong,这不是重点,具体见最后的源代码。

真正的功能(重点)
1

现在,我们来实现真正的功能!!首先,创建一个作业内核对象:HANDLE hJob=CreateJobObject(NULL,NULL);

2

接着,我们根据用户的选项(Edit编辑框和Check的值来初始化两个结构)这里,我初始化了两个结构,其实还有一个另一个结构可以用于进行 安全限制 的,但由于这些功能需要用户有一定的基础知识而不常用,所以这里没有提供这个接口。以下是源代码(耐得住寂寞才会成功):VOID OnSetInformation(HWND hWnd){ /*基本限制*/ JOBOBJECT_BASIC_LIMIT_INFORMATION jbli={0}; LARGE_INTEGER li={0}; li.LowPart=GetDlgItemInt(hWnd,IDC_PerProcessUserTimeLimit,NULL,FALSE); jbli.PerProcessUserTimeLimit=li; li.LowPart=GetDlgItemText(hWnd,IDC_PerJobUserTimeLimit,NULL,FALSE); jbli.PerJobUserTimeLimit=li; jbli.ActiveProcessLimit=GetDlgItemInt(hWnd,IDC_ActiveProcessLimit,NULL,FALSE); jbli.MinimumWorkingSetSize=GetDlgItemInt(hWnd,IDC_MinimumWorkingSetSize,NULL,FALSE); jbli.MaximumWorkingSetSize=GetDlgItemInt(hWnd,IDC_MaximumWorkingSetSize,NULL,FALSE); jbli.SchedulingClass=GetDlgItemInt(hWnd,IDC_SchedulingClasss,NULL,FALSE); TCHAR szPriorityClass[10]; GetWindowText(GetDlgItem(hWnd,IDC_PriorityClass),szPriorityClass,_countof(szPriorityClass)); //进程优先级 if(lstrcmp(szPriorityClass,_T("高"))) jbli.PriorityClass=THREAD_PRIORITY_HIGHEST; else if(lstrcmp(szPriorityClass,_T("高于正常"))) jbli.PriorityClass=THREAD_PRIORITY_ABOVE_NORMAL; else if(lstrcmp(szPriorityClass,_T("正常"))) jbli.PriorityClass=THREAD_PRIORITY_NORMAL; else if(lstrcmp(szPriorityClass,_T("低于正常"))) jbli.PriorityClass=THREAD_PRIORITY_BELOW_NORMAL; else if(lstrcmp(szPriorityClass,_T("低"))) jbli.PriorityClass=THREAD_PRIORITY_LOWEST; else if(lstrcmp(szPriorityClass,_T("空闲"))) jbli.PriorityClass=THREAD_PRIORITY_IDLE; jbli.LimitFlags=JOB_OBJECT_LIMIT_PROCESS_TIME | JOB_OBJECT_LIMIT_JOB_TIME | JOB_OBJECT_LIMIT_WORKINGSET | JOB_OBJECT_LIMIT_ACTIVE_PROCESS | JOB_OBJECT_LIMIT_AFFINITY | JOB_OBJECT_LIMIT_SCHEDULING_CLASS; SetInformationJobObject(hJob,JobObjectBasicLimitInformation,&jbli,sizeof(jbli)); /*UI限制*/ JOBOBJECT_BASIC_UI_RESTRICTIONS jbur={0}; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMITEXITWINDOWS),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_EXITWINDOWS; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMITREADCLIPBOARD),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_READCLIPBOARD; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMITWRITECLIPBOARD),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_WRITECLIPBOARD; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMITDESKTOP),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_DESKTOP; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMITSYSTEMPARAMETERS),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_SYSTEMPARAMETERS; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMITDISPLAYSETTINGS),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_DISPLAYSETTINGS; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMITGLOBALATOMS),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_GLOBALATOMS; if(SendMessage(GetDlgItem(hWnd,IDC_UILIMIT_HANDLES),BM_GETCHECK,0,0)) jbur.UIRestrictionsClass|=JOB_OBJECT_UILIMIT_HANDLES; SetInformationJobObject(hJob,JobObjectBasicUIRestrictions,&jbur,sizeof(jbur)); AddText(GetDlgItem(hWnd,IDC_JOBMSG),_T("设置限制完成!"));}

3

以上就是所有的操作了!看懂了源代码你就已经成功了!!如果你没看懂,没关系,这里是一些解释:贯穿代码中的两个结构:JOBOBJECT_BASIC_LIMIT_INFORMATION  jbli={0} //基本限制JOBOBJECT_BASIC_UI_RESTRICTIONS  jbur={0} //UI限制贯穿代码中的两次函数调用:SetInformationJobObject(hJob,JobObjectBasicLimitInformation,&jbli,sizeof(jbli));SetInformationJobObject(hJob,JobObjectBasicUIRestrictions,&jbur,sizeof(jbur));没错,你所看到的所有冗长的操作都是根据用户的操作调整这两个数据结构而已!!而关于这两个数据结构和SetInformationJobObject,MSDN上的解释非常好(再加上我想偷懒),这里就不再解释了。不过,听说MSDN是英文版的~~2012是这样~~为了帮助大家更容易理解,这里我引用一篇文档,链接见最后的注意事项1(正文不能有链接~~)当然,也可以参考:《Windows核心编程5 Via C/C++》第五张<作业>

调试程序
1

成功编写,不代表你的软件毫无差错!!调试是很重要的。我们来做个实验。打开软件沙箱。并勾选“禁止注销...”并单击“设置限制”。

2

运行一个 “定时关机”程序(该程序通过ExitWindowsEx来关机)(当然,是我自己写的)。

3

嘀嘀嘀,等待1分钟。哎呀,时间到了,然而这并没什么卵用,呵~我的系统安然无恙!!

4

再来一个,前段时间我的一位同学编了一个小程序来捉弄我~~这个程序会打开100个cmd窗口~~然而,我的“软件沙箱”帮我渡过了难关!!来,有图有真相!!妈妈吖,我差点挂了(这CPU占用率是很高的!),殊不知我一关掉“软件沙箱”(这时软件沙箱会终止作业中的所有进程【通过调用TerminateJobObject】【详见源代码】),全部cmd窗口都没了~~

5

我们再来玩玩Microsoft的spy++(这家伙挺厉害的)spy++的启动需要管理员权限,所以也需要用管理员权限来启动“软件沙箱”勾选“禁止使用进程外部用户对象”并启动spy++看,spy++中啥都没有

6

最后,我们拿Excle开刀!懒得解释,看图吧Word和PowerPoint就弹出启动框后直接退出了~~一点提示都没有。Acess就什么事也没有。

注意事项
1

http://wenku.baidu.com/view/b0a7226648d7c1c708a145c1.html?from=search【我严重认为这个家伙是复制《Windows核心编程》的,内容与原著一模一样!!】

2

软件沙箱示例程序链接:https://pan.baidu.com/s/1c14cKik【软件沙箱】文件夹内其中分为一个安装包(给只想使用的用户)和一个源代码压缩文件(给求知欲强的用户)

推荐信息