Пример #1
0
bool ModifyReparsePoint(const wchar_t *Object,const wchar_t *NewData)
{
	bool Result=false;
	LPBYTE szBuff=new BYTE[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
	if(szBuff)
	{
		PREPARSE_DATA_BUFFER rdb=reinterpret_cast<PREPARSE_DATA_BUFFER>(szBuff);

		if (GetREPARSE_DATA_BUFFER(Object,rdb))
		{
			bool FillResult=false;

			switch (rdb->ReparseTag)
			{
				case IO_REPARSE_TAG_MOUNT_POINT:
				{
					string strPrintName,strSubstituteName;
					ConvertNameToFull(NewData,strPrintName);
					strSubstituteName=L"\\??\\";
					strSubstituteName+=(strPrintName.CPtr()+(HasPathPrefix(strPrintName)?4:0));
					FillResult=FillREPARSE_DATA_BUFFER(rdb,strPrintName,strPrintName.GetLength(),strSubstituteName,strSubstituteName.GetLength());
				}
				break;
				case IO_REPARSE_TAG_SYMLINK:
				{
					string strPrintName=NewData,strSubstituteName=NewData;

					if (IsAbsolutePath(NewData))
					{
						strSubstituteName=L"\\??\\";
						strSubstituteName+=(strPrintName.CPtr()+(HasPathPrefix(strPrintName)?4:0));
						rdb->SymbolicLinkReparseBuffer.Flags=0;
					}
					else
					{
						rdb->SymbolicLinkReparseBuffer.Flags=SYMLINK_FLAG_RELATIVE;
					}

					FillResult=FillREPARSE_DATA_BUFFER(rdb,strPrintName,strPrintName.GetLength(),strSubstituteName,strSubstituteName.GetLength());
				}
				break;
			}

			if (FillResult)
			{
				Result=SetREPARSE_DATA_BUFFER(Object,rdb);
			}
			else
			{
				SetLastError(ERROR_INSUFFICIENT_BUFFER);
			}
		}
		delete[] szBuff;
	}
	return Result;
}
Пример #2
0
bool ModifyReparsePoint(const string& Object,const string& NewData)
{
	block_ptr<REPARSE_DATA_BUFFER> rdb(MAXIMUM_REPARSE_DATA_BUFFER_SIZE);
	if (!GetREPARSE_DATA_BUFFER(Object, rdb.get()))
		return false;

	switch (rdb->ReparseTag)
	{
	case IO_REPARSE_TAG_MOUNT_POINT:
		{
			const auto strPrintName = ConvertNameToFull(NewData);
			const auto strSubstituteName = KernelPath(NTPath(strPrintName));
			if (!FillREPARSE_DATA_BUFFER(rdb.get(), strPrintName, strSubstituteName))
			{
				SetLastError(ERROR_INSUFFICIENT_BUFFER);
				return false;
			}
		}
		break;

	case IO_REPARSE_TAG_SYMLINK:
		{
			const auto& strPrintName = NewData;
			auto strSubstituteName = NewData;

			if (IsAbsolutePath(NewData))
			{
				strSubstituteName = KernelPath(NTPath(strSubstituteName));
				rdb->SymbolicLinkReparseBuffer.Flags=0;
			}
			else
			{
				rdb->SymbolicLinkReparseBuffer.Flags=SYMLINK_FLAG_RELATIVE;
			}

			if (!FillREPARSE_DATA_BUFFER(rdb.get(), strPrintName, strSubstituteName))
			{
				SetLastError(ERROR_INSUFFICIENT_BUFFER);
				return false;
			}
		}
		break;

	default:
		return false;
	}

	return SetREPARSE_DATA_BUFFER(Object,rdb.get());
}
Пример #3
0
bool CreateReparsePoint(const string& Target, const string& Object,ReparsePointTypes Type)
{
	bool Result=false;

	{
		switch (Type)
		{
			case RP_HARDLINK:
				break;
			case RP_EXACTCOPY:
				Result=DuplicateReparsePoint(Target,Object);
				break;
			case RP_SYMLINK:
			case RP_SYMLINKFILE:
			case RP_SYMLINKDIR:
				{
					os::fs::file_status ObjectStatus(Object);
					if(Type == RP_SYMLINK)
					{
						Type = os::fs::is_directory(Target)? RP_SYMLINKDIR : RP_SYMLINKFILE;
					}
					if (imports.CreateSymbolicLinkW && !os::fs::exists(ObjectStatus))
					{
						Result=os::fs::CreateSymbolicLink(Object,Target,Type==RP_SYMLINKDIR?SYMBOLIC_LINK_FLAG_DIRECTORY:0);
					}
					else
					{
						const auto ObjectCreated = Type==RP_SYMLINKDIR?
							os::fs::is_directory(ObjectStatus) || os::fs::create_directory(Object) :
							os::fs::is_file(ObjectStatus) || os::fs::file(Object, 0, 0, nullptr, CREATE_NEW);

						if (ObjectCreated)
						{
							block_ptr<REPARSE_DATA_BUFFER> rdb(MAXIMUM_REPARSE_DATA_BUFFER_SIZE);

							rdb->ReparseTag=IO_REPARSE_TAG_SYMLINK;
							const auto& strPrintName = Target;
							auto strSubstituteName = Target;

							if (IsAbsolutePath(Target))
							{
								strSubstituteName = KernelPath(NTPath(strSubstituteName));
								rdb->SymbolicLinkReparseBuffer.Flags=0;
							}
							else
							{
								rdb->SymbolicLinkReparseBuffer.Flags=SYMLINK_FLAG_RELATIVE;
							}

							if (FillREPARSE_DATA_BUFFER(rdb.get(), strPrintName, strSubstituteName))
							{
								Result=SetREPARSE_DATA_BUFFER(Object,rdb.get());
							}
							else
							{
								SetLastError(ERROR_INSUFFICIENT_BUFFER);
							}
						}
					}
				}
				break;
			case RP_JUNCTION:
			case RP_VOLMOUNT:
			{
				const auto strPrintName = ConvertNameToFull(Target);
				auto strSubstituteName = KernelPath(NTPath(strPrintName));
				block_ptr<REPARSE_DATA_BUFFER> rdb(MAXIMUM_REPARSE_DATA_BUFFER_SIZE);
				rdb->ReparseTag=IO_REPARSE_TAG_MOUNT_POINT;

				if (FillREPARSE_DATA_BUFFER(rdb.get(), strPrintName, strSubstituteName))
				{
					Result=SetREPARSE_DATA_BUFFER(Object,rdb.get());
				}
				else
				{
					SetLastError(ERROR_INSUFFICIENT_BUFFER);
				}
			}
			break;
		}
	}

	return Result;
}
Пример #4
0
bool WINAPI CreateReparsePoint(const wchar_t *Target, const wchar_t *Object,DWORD Type)
{
	bool Result=false;

	if (Object && *Object && Target && *Target)
	{
		switch (Type)
		{
			case RP_EXACTCOPY:
				Result=DuplicateReparsePoint(Target,Object);
				break;
			case RP_SYMLINK:
			case RP_SYMLINKFILE:
			case RP_SYMLINKDIR:
				if(Type == RP_SYMLINK)
				{
					DWORD Attr = apiGetFileAttributes(Target);
					Type = ((Attr != INVALID_FILE_ATTRIBUTES) && (Attr&FILE_ATTRIBUTE_DIRECTORY)? RP_SYMLINKDIR : RP_SYMLINKFILE);
				}
				if (ifn.pfnCreateSymbolicLink)
				{
					Result=apiCreateSymbolicLink(Object,Target,Type==RP_SYMLINKDIR?SYMBOLIC_LINK_FLAG_DIRECTORY:0);
				}
				else
				{
					bool ObjectCreated=false;

					if (Type==RP_SYMLINKDIR)
					{
						ObjectCreated=apiCreateDirectory(Object,nullptr)!=FALSE;
					}
					else
					{
						File file;
						if(file.Open(Object,0,0,nullptr,CREATE_NEW))
						{
							ObjectCreated=true;
							file.Close();
						}
					}

					if (ObjectCreated)
					{
						LPBYTE szBuff=new BYTE[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
						if(szBuff)
						{
							PREPARSE_DATA_BUFFER rdb=reinterpret_cast<PREPARSE_DATA_BUFFER>(szBuff);
							rdb->ReparseTag=IO_REPARSE_TAG_SYMLINK;
							string strPrintName=Target,strSubstituteName=Target;

							if (IsAbsolutePath(Target))
							{
								strSubstituteName=L"\\??\\";
								strSubstituteName+=(strPrintName.CPtr()+(HasPathPrefix(strPrintName)?4:0));
								rdb->SymbolicLinkReparseBuffer.Flags=0;
							}
							else
							{
								rdb->SymbolicLinkReparseBuffer.Flags=SYMLINK_FLAG_RELATIVE;
							}

							if (FillREPARSE_DATA_BUFFER(rdb,strPrintName,strPrintName.GetLength(),strSubstituteName,strSubstituteName.GetLength()))
							{
								Result=SetREPARSE_DATA_BUFFER(Object,rdb);
							}
							else
							{
								SetLastError(ERROR_INSUFFICIENT_BUFFER);
							}
							delete[] szBuff;
						}
					}
				}

				break;
			case RP_JUNCTION:
			case RP_VOLMOUNT:
			{
				string strPrintName,strSubstituteName;
				ConvertNameToFull(Target,strPrintName);
				strSubstituteName=L"\\??\\";
				strSubstituteName+=(strPrintName.CPtr()+(HasPathPrefix(strPrintName)?4:0));
				BYTE szBuff[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
				PREPARSE_DATA_BUFFER rdb=reinterpret_cast<PREPARSE_DATA_BUFFER>(szBuff);
				rdb->ReparseTag=IO_REPARSE_TAG_MOUNT_POINT;

				if (FillREPARSE_DATA_BUFFER(rdb,strPrintName,strPrintName.GetLength(),strSubstituteName,strSubstituteName.GetLength()))
				{
					Result=SetREPARSE_DATA_BUFFER(Object,rdb);
				}
				else
				{
					SetLastError(ERROR_INSUFFICIENT_BUFFER);
				}
			}
			break;
		}
	}

	return Result;
}