DLL loading with hardlink - windows

I am trying to devise a method which helps to load DLL from a common location for various products. This helps the following directory structure to avoid file replication.
INNSTALLDIR/Product1/bin
INNSTALLDIR/Product2/bin
..
INNSTALLDIR/ProductN/bin>
Instead of replicating DLLs in each product's bin directory above, I can create a DLL repository/directory - 'DLLrepo' in INSTALLDIR and make all product exceutables load from it. I am thinking to do this by creating hardlink to each DLL in 'DLLrepo' in each product's bin directory. This will help to address platforms starting from WinXP. Using 'probing' method can address only Windows server 2008 and above.
I like to get your opinion if this approach looks like a reasonable solution.
When we create hardlink to a file, the explorer or DIR command doesn't account valid size of the folder involving link. It account the actual data size in the linked file in total size of the directory. This is a known issue in windows if I am not wrong. Is there any utility that I can use to verify the actual folder size? Is it possible to use 'chkdisk' on a directory path? Another thing which I like to know is to get the list of links created on file data.

When we create hardlink to a file, the
explorer or DIR command doesn't
account valid size of the folder
involving link. It account the actual
data size in the linked file in total
size of the directory. This is a know
issue in windows if I am not wrong. Is
there any utility that I can use to
verify the actual folder size?
I can provide an answer, of sorts, for this part of the question. When you create file hardlinks, there's not really any concept of which "file" is the original. Each of them points to the space on disk that the data is occupying and modifying the file via any of these references affects the data that's seen when accessing it via any other hardlink. As such it's less a known "issue" and more of a "this is how it works".
As such, there's no way to verify "actual folder size" unless you're looking at the size of the highest common parent folder of the folders that contain the links. At that point you can start single-counting each hard-link to get an accurate idea of space used on disk.

Related

Is there a way to shorten Network Drive file paths?

We are currently using Network Locations to access our company SharePoint files.
We decided to use Network Location instead of OneDrive, because OneDrive has a delay of 5-15 between a person uploading a file and other people seeing the file on their file explorer.
However, we ran into a problem with Network Locations, since the file explorer only allows file paths up to 260 characters (MAX_PATH). Our Network Location starts with
https://XXXXXXXXXX.sharepoint.com/Shared Documents/{Enter Folder names here}
Is there a way of reducing this start of the file path? Since if it crosses the max path limit, the files wont be accessible through file explorer, only the SharePoint site itself.
I know it would be possible to change the "SHared Documents" part to, for example, SD. But does anyone know how this will affect files that are for example referencing to other files with that name?
Thanks! :)
We could not reduce this start of the file path of the Internent address.
What do other file references to library names mean?
Normally, change the library name will have no impact to files.

On Windows/NTFS can a symbolic link be moved to another computer?

For the purposes of a security test involving Windows servers, I would like to attempt uploading a Symbolic link to a Windows web application. However, based on the information officially available, it is unclear whether Windows hard links (Which I suppose are the same as NTFS junctions) exist as a file that can be copied from the hard disk the same way it does on Linux. It's vague, but I get the sense that NTFS junctions are some other kind of file system artifacts which is different than "regular" files - I can't find the documentation to confirm or deny this. I.E NTFS I want to know if NTFS supports the direct manipulation of the symlink record such that I could move the symlink to a different computer.
I am aware that Windows softlink files (.lnk) are not limited in this way, but they do not suit the purposes of the test.
My Aim is to copy a symlink off of a virtual machine, and then upload it to the server which I am testing.
Is this possible? (I am under the impression it is not.) From what I have seen absolutely every program on Windows would regard the hardlink as the destination file. Is there a way around this, perhaps by using a special editor to temporarily corrupt the file? If the symlink exists as a normal file on the file system can the symlink be altered so it can moved to a non-Windows OS for further use?
Let me know if this would be a better question for server fault. Since this is not directly about security, and is more of mundane technical problem in the service of a security exercise, I don't think it would fit on Stack Exchange security.
It's hard to provide a very direct answer. I work on a backup/repair/imaging project, and I copy whole disk images to a server via a web service - so, it's possible to do what you want, but there's a lot to consider.
Hardlinks
It is generally assumed that hardlinks cannot be distinguished from each other, however, there is a subtle difference between linked files and their "original" file. That difference is that queries to the $MFT (using USN-related arguments on the winapi function DeviceIOControl) will only return one of the files. This may be considered the original file. You can then call the winapi function NtQueryInformationFile to enumerate the hard links.
Symlinks and junctions are different animals...
You can know that a folder is a junction or a symlink, by getting the attributes from it. There's a ReparsePoint flag in the attributes if it's a junction or a symlink. BTW - the difference between junctions and symlinks is that the junction is a redirect to another location on the same volume, while a symlink is a redirect to an off-volume location. The redirect target is always another folder either way.
What's interesting is that both symlinks and junctions look and act like folders, while they are really files containing redirect information. When you open 'em, NTFS will normally look at the redirect, and open the redirect target. NTFS checks the permissions at the redirect target, so as an attack, this might not be a robust strategy.
When opening a junction/symlink, you can add a flag FILE_FLAG_OPEN_REPARSE_POINT. When you do this, NTFS does not perform the redirect, but opens the content, which is actually redirect information, and assuming you know the format of that information, it is possible to reconstruct the junction/symlink at the server. Note that the redirect may point to a location that may not exist, or may exist only temporarily. This is expected as some network resources may not always be available.
So, in short, it's possible to copy a junction or a symlink...while copying a hard link nominally means copying the file...with the foregoing subtleties in mind. You can create a hard link manually, too, as long as the target file exists.
With hardlinks, there's one interesting kink in the NTFS security picture. If a user has access to a file, and you create a hardlink to that file in a folder the user doesn't have access to, the user can still open that file using the path to the hard link. This is because the link and the original file are both pointing to the same file (and security info) on disk. Permissions changed on any of the links affect all the links. Without knowing this, you can inadvertently wreak havoc on a file system :-)
I know this is a bit helter-skelter, so let me summarize this way:
NTFS directory entries can be folders or files. Hardlinks are directory entries that all point to one file. Symlinks and junctions are really files that act like folders for most practical purposes (until you know how to get at the redirect info as described above).
AFAIR, NTFS (directory) junctions are actually symbolic links. The juctnion is implemented as a special file attribute called repars point that contains the link target.
Hardlinks, on the other hand, are implemented as direct references to the base MFT record of the target file and are stored as regular entries inside directory tree. You actually cannot distinguish a hardlink from the "original" file (every file and directory actually has at least one hardlink since it is contained somewhere within the directory tree).
If you wish to copy a symbolic link itself, you need to know that it is a symbolic link and extract the information about its target. File operations (except deletion and, probably, renamng) are redirected to the link target. So, you can, in general, copy a symbolic link by creating its exact copy in the destination area.
The actual question is, whether the interface you are using to perform the copy operation allows you to create symbolic links on the target.

Difference between Program Files and ProgramData?

How do I decide which of my application's files go in Program Files (FOLDERID_ProgramFilesX64) and which go in ProgramData? (FOLDERID_ProgramData)? I don't understand what the reason is for splitting up my application's fixed files into these two categories or how I should decide which file goes in what.
For example - image files which my application displays, are they "program" or "data"?
Is there any problem with just putting everything under one or the other?
The application is installed for All Users and has no user-specific configuration files or data.
Program Files is for executables and other static files that came as part of the installation. ProgramData is for user-agnostic data generated during execution such as shared cache, shared databases, shared settings, shared preferences, etc. User-specific data goes in the AppData folder. Note that these are for non-user-visible data. User-visible data belongs in the documents folder (or music, video, custom sibling folder, etc.).
Please see Special Folders and Custom Folders for a detailed explanation. Note that the terminology used varies slightly between the name used in the documentation here, the name of the folder, and the name used by various enumerations used to get these paths from the system.

Directory location for writing cache file

Hi I am trying to find out what is the best location to save a cache file.
I have an Windows form application that updates user's data from the server using a custom tool.
I want to write the timestamp of the latest updates done on user's machine in the cache file.
Where is the best location for keeping this file:
1. in application directory (c:\program files..)
2. in a temp location e.g. Users profile folder or c:\windows\temp
3. in any location (e.g. c:\dataupdates) where user has full access to read/write to.
Not in the application directory. That much is clear. :) The application directory shouldn't even be writable by the program (or actually by the user account that runs the program). Although some applications still use this location, it has actually been deprecated since Windows 95, I believe, and it has become a real pain since the more rigid UAC applied in Windows Vista and 7.
So the most obvious options are:
The temp folder, which is for temporary files. Note however, that you will need to clean those files up. Temp folder is not automatically cleared by default, so adding new files all the time will consume increasingly much space on the hard drive. On the other hand, some users do clear their temp folders, or may have scripts installed that do that for them, so you cannot trust such files to remain. Also, this is not always C:\Temp of whatever. You'll have to ask Windows what the location is.
You can pick 'any' location. Note that you cannot write anywhere. You cannot even expect the C drive to exist. If you choose this, then you have to make it a configurable setting.
The %app data% directory, my personal favorite, which is a special directory for applications to store their data in. The advantage is, that you can ask Windows for this location, and you can make up a relative path based on that directory, so you don't really have to make it an application setting. For more info on how to get it, see also this question: C# getting the path of %AppData%
I would definitely choose the App Data path for this purpose.

Working directories of files used in Windows applications

Where does an application look when a file is searched for? Where is it created? It's rarely realistic to always specify the absolute path. E.g. I tried saving text files that were going to be used in a Visual Studio 2010 app in the local bin of the project solution, but always got a run-time error.
It's usually the folder it was called from. You can find it using _getcwd: http://msdn.microsoft.com/en-us/library/sf98bd4y%28VS.80%29.aspx
If you use a relative path, the path you supply is combined with the working directory of the process.
It's very hard to maintain control over the working directory of a GUI process. That's because GUI processes tend to be started in lots of different ways. What's more, file dialogs have a tendency to change working directory. Finally, the working directory is shared between all threads in the process, and can be changed by any thread. There are lots of pitfalls.
So in a GUI process I suggest that you never use relative paths. Or, if you do use relative paths, you convert them to absolute paths before using them. And perform that conversion against a well-defined root path.
Unless you are writing a portable app, you should not expect to be able to save to the directory which contains the executable file. On modern systems executable files are often located in read-only directories.
If you want to save user settings, save them at an appropriate location in the user's profile.
On the other hand, if you are wanting to read files, that you never modify, then it's reasonable to store them alongside the executable. But even in that case, open the file using a full absolute path. Create that path by combining the directory which contains the executable, with the relative path to the file.
So, to summarise, you said:
It's rarely realistic to always specify the absolute path.
But I disagree. I would counter that using an absolute path is very often the best option. But you don't have to hard code the absolute path. You can, and should, create it at runtime.

Resources