Windows C++实现文件共享
一、背景
在Windows上做应用开发,有时会遇到一种场景:要使用的文件放在其他机器上,由另外的机器取访问存放文件的电脑。
存放文件的节点系统可以是Windows、Linux或其他系统,但为了用户能方便查看文件,一般还是会选择Windows系统。一台硬件低配的机器即可,搭载多张磁盘,做成磁盘阵列来实现数据冗余(以防数据丢失)。
二、数据访问
接下来要考虑的是,把数据放到其他机器上后,要如何访问到那些数据呢?方法很多!比如在存放文件的系统上搭载一个ftp或者http服务器。
但这种方案有个很明显的问题,就是麻烦:首先要搭服务器,然后就是存取数据的时候有个明显的下载和上传过程,很难做到像访问本地文件一样的效果。比如我们想调用ReadFile和WriteFile接口时,就得先把文件下载到本地,然后才可以调用这些接口。当然,也可以跳过类似与这类的读写接口,直接从网络中读取数据到缓存,或者将缓存数据写入到网络。如果是小文件的话,问题读写操作的不大,大文件的话,就可能出现很多问题。
有一种方式:共享文件夹,可以很好地解决这种问题。访问共享文件,体验上就如同访问本地文件。
共享文件的设置,除了用手动,还可以自己写脚本或者调用API。这边介绍使用API的方式,实现自己的程序设置共享。
三、代码实现
1. 使用的API:NetShareAdd
2. 主要参数介绍:如下代码
SHARE_INFO_502 info;
info.shi502_netname = (LPTSTR)TEXT("TESTSHARE");
info.shi502_type = STYPE_DISKTREE;
info.shi502_remark = (LPTSTR)L"";
info.shi502_permissions = ACCESS_ALL;
info.shi502_max_uses = -1;
info.shi502_current_uses = 0;
info.shi502_path = (LPTSTR)TEXT("C:\Windows");
info.shi502_passwd = (LPTSTR)L"";
info.shi502_reserved = 0;
info.shi502_security_descriptor = NULL;
其中,shi502_security_descriptor是比较主要且稍微复杂的参数成员,它可以控制共享目录的权限,是最高的所有权限,还是只读、只写或是执行权。这是个安全描述符参数,很多API都会用到,如CreateProcess。当然,如果设置为空,那就是开放所有权限。
3. 修改共享权限参数:NetShareSetInfo。在添加完共享后,想要修改共享的权限,就可以使用该接口,参数与NetShareAdd相似。
4. SHARE_INFO_x安全描述示例:
SID_IDENTIFIER_AUTHORITY world_auth = SECURITY_WORLD_SID_AUTHORITY; AllocateAndInitializeSid(&world_auth, 1, SECURITY_WORLD_RID, 0, 0, 0, 0, 0, 0, 0, &sid); EXPLICIT_ACCESS access; access.grfAccessPermissions = GENERIC_READ | GENERIC_EXECUTE/* | GENERIC_ALL*/; access.grfAccessMode = SET_ACCESS; access.grfInheritance = NO_INHERITANCE; access.Trustee.pMultipleTrustee = 0; access.Trustee.MultipleTrusteeOperation = NO_MULTIPLE_TRUSTEE; access.Trustee.TrusteeForm = TRUSTEE_IS_SID; access.Trustee.TrusteeType = TRUSTEE_IS_GROUP; access.Trustee.ptstrName = (LPWSTR)sid; SetEntriesInAcl(1, &access, 0, &dacl); // 创建安全描述符 SECURITY_DESCRIPTOR sd; InitializeSecurityDescriptor(&sd, SECURITY_DESCRIPTOR_REVISION); // 添加访问控制列表 SetSecurityDescriptorDacl(&sd, TRUE, dacl, FALSE); // 设置创建好的安全描述 info.shi502_security_descriptor = &sd;
参考资料:
