Need Windows chmod777 Equivalent - c#

I need to set permissions on a file, so that all users on the system can read and write to it. This is related to an installer, so I do not know the user names ahead of time. The installer runs as admin, so the log file requires admin access afterwards. So I need to explicitly set the permissions, during the install, so that referencing programs don't need to be run as admin.
In essence, I'm looking for a solution that can give me the equivalent of chmod777 in Windows.
I would prefer a solution that works for both Win7 and WinXP. I would like a solution that is through command line, which I can then script. Or a solution using C# or java.

All modern Windows OS's have a build-in group called "Everyone" that is the equivalent of the UNIX "other" permissions. Even non-logged-in users are part of the Everyone group. From there you can give "Everyone" read, write, and modify ("change") permissions. You could, if you were completely insane, give Everyone "full control" but that actually allows them to take ownership and change the permissions, so please don't do that :)
To actually apply these permissions you can use a number of techniques
From a command-line, you can run cacls <file name> /g Everyone:RWC
In .NET you can create an ACL for the NT Account with WellKnownSidType.WorldSid then apply it to a file, as in this article: http://social.msdn.microsoft.com/forums/en-US/csharpgeneral/thread/c513ca26-9bf8-4e39-a993-4ebf90aaece6/
You can use WMI, as per How to change file permissions with WMI? (should work in any WMI-enabled language)
You could use the native Win32 file permission APIs (via P/Invoke or JNI).

In C#, you can get an NTAccount object, and get the file's FileSecurity object, and use the FileSecurity object's AddAccessRule method to set permissions.
See the MSDN forum post below for more detailed instructions.
http://social.msdn.microsoft.com/forums/en-US/csharpgeneral/thread/c513ca26-9bf8-4e39-a993-4ebf90aaece6/

Related

Delete stubborn registry key

Description
One driver left a mess in the registry (even when I uninstalled it from the system). If I check the security setting it will not display anything in “Group or user names”. And when I check the owner it shows only “Unable to display current owner.”. When I want to delete the registry keys I have to:
Take the ownership.
Add group.
Delete the key.
The problem is that each registry has several sub keys and I have to repeat the process on each key. Inherit permission option will not work in Registry Editor. And yes, I am running Registry Editor in administrator mode.
Problem
I wanted to write a simple C# code that would loop and delete all keys. I have found some code samples, but in my case any OpenSubKey call would fail with error:
System.Security.SecurityException: Requested registry access is not allowed.
How can I change the ownership if any call of OpenSubKey function would fail? Is there any other command where I can claim the ownership and then delete the registry key?
Thank you for the support
Just as you knew to run the Registry Editor as an administrator in order to ensure that you would have the appropriate privileges to modify/delete registry keys, you need to do the same thing for your C# application.
Because you forgot to do this, the System.Security.SecurityException is being thrown as a reminder. As the exception message says, you do not have the privileges to modify/delete the registry key(s).
To solve the problem, you must execute your C# application with administrative privileges. You can either do this manually, or add a manifest to your application that will cause it to automatically demand administrative privileges.
This is half an answer.
This knowledge base article explains how to take ownership of a key that you don't have access to.
In short, you need to enable the "Take Ownership" privilege and open the key with WRITE_OWNER access. You can then set the owner.
Note that this only works when you run your code as an Administrator.
However, I don't know if you can do this in C# using the built in functions, or if you would need to use interop to call the native APIs. If the latter, it would probably be quicker to use C/C++.
Or you could use the SubInAcl tool. It can take ownership of files, registry keys, etc.
To be clear you right click and run as administrator when you talk about running it in administrator mode - this is elevated privilege and it wont happen by simply double clicking. Even if you login as admin you must right click and run as administrator to get elevated.
My problem I fixed by writing to CURRENT_USER and not LOCAL_MACHINE now I see that your problem is not actually solved by elevation and granting. Your security descriptors stored in the Registry were probably corrupted by garbage writes from the AWOL driver or whatever happened. This means you wont be able to do much, including fix yourself or a new user.
You may not be able to run CCleaner either until we clear the permissions issue. However you can boot into safe mode and run sfc /scannow and chkdsk - the sfc fixed one persons issue similar however it may be risky so do at own risk but it looks promising and I probably would have already done the scannow before I tried anything else. Safemode +sfc/scannow
I would backup data and wipe it ASAP much faster. I did find instructions for various OS on the matter of corrupt security descriptors - for Win 8 and 7 so you should not have problems and look like they will require Safe Mode
Good Luck!

How to give Create, Read and Modify permissions to all users for a file created by my application in C:\ProgramData?

My application basically creates an XML file in C:\ProgramData\MyAppFolder and dumps config settings in it.
I need to allow even standard users to have permission to add or delete settings to these config files. Right now I see that standard users only have read/execute permission but not "Full Control".
I've seen other questions being answered with ways to modify permissions to that particular folder but I don't want to change the default permission level, since it might be reset by a system admin.
If C:\ProgramData can't give that access to all users, is there any folder that best suits the needs of application?
EDIT:
My initial question might be misleading. I don't want to give rights to users, but rather allow the application to modify the XML file when it is run by all users.
DECISION:
I think changing the permissions while creating the folder in ProgramData is the only option.
And if that's not possible, CommonDocuments is the way to go.
Thanks Eve.
I would use a folder in the Environment.SpecialFolder enum.
Example:
var path = Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData);
Assuming you have an installer for your application, your installer can create a subfolder in the common appdata directory (aka C:\ProgramData) which your application will have read/write access to. Depending on your choice of installation technology you can set the permissions on that folder as well, although that may be overkill. I know with WiX basically all you have to do is a per-machine installation and make sure that sub folder gets created.
Users should not be allowed to write arbitrary data to this directory. This is equivalent to regular users being able to modify the C:\Users\AllUsers directory. If users need to be modifying this directory you have serious design flaws and should reconsider this approach. What should happen is the users are given GUI interface to interact with that manipulates these values behind the scenes without giving them direct access, similar to how getters/setters work in most programming languages. Needless to say it is a very large security hole when regular users can corrupt a system for other users.
UPDATE
I don't want to give users direct access to the file. My question
might have been misleading. I want to allow the program to have full
control on the file even when it being run by all users. I'm actually
doing this: "users are given GUI interface to interact with that
manipulates these values behind the scenes without giving them direct
access"
This article which has far too much information to post here, will provide details on remaining secure as to not leak permissions. The first thing you want to do is make sure that your application user is in its own group and cannot login/have any special permissions. What you can than do is have this group added to the directory with write permissions, which would allow this application to perform these tasks. If that is not possible you will need to work within UAC to not break the security of the system as is detailed in the article above.
Second Update
Thanks for the link. Any suggestions on some other folder which can do
the job, rather than messing with the permissions?
Sure you can write it into the directory where the application is written to, i.e. C:\Program Files\Some Awesome Program, this keeps everything in one place, and you only have to worry about your user/group and anything that the person who installed it has allowed for. It also prevents other people from messing with it unless of course they are administrators.

FileSystemWatcher surpassing file system permissions

While experimenting with FileSystemWatcher, I've found out that it somehow surpasses my user account's permissions to files and folders, and will raise change events with information about what has changed in files and folders that you don't even have access to.
I have two questions about that:
1) Why does this happen ?
2) Is this a problem in the AD configuration ? how do I fix it ?
3) Is there any way to gather these files, or even create a FileSystemInfo of them to get more info about the files (not only the changes made on them) ?
As far as I've tried, only the FileSystemWatcher immune to the restrictions, I can't run any other thing over it, here's a list of what I've tried:
File.Exists
Directory.Exists
FileInfo instance on found files
DirectoryInfo instance on found files
File.Copy
File.Delete
Update: Tried helge's solution, with somethin similar to what he's sugested, not through windows' api, but through the command prompt:
robocopy /B \myserver\folder c:\somefolder
Best command name ever.
You can check through robocopy that /B stands for "backup mode", which is what helge's suggested that would be the cause to this security surpassing.
I'll try anything, I want to find out what exactly causes FileSystemWatcher to be able to watch folders I do not have permission to open. Knowing why, I want to learn both how to block FileSystemWatcher, and how to gather found files.
I'd make a survey if I was with my personal account. Please, can someone help me ? I'll write a blog post about the solution, among other things that might help anyone with the same doubt in the future.
According to this answer on SO the FileSystemWatcher is based on the API function ReadDirectoryChangesW. If that is true it explains the behavior witnessed by you - and why that is not a security hole.
As documented on MSDN ReadDirectoryChangesW needs the privilege SeBackupPrivilege (which is requested by the parameter FILE_FLAG_BACKUP_SEMANTICS to CreateFile). If a file is opened in that mode, the returned handle grants full access to the file, circumventing access checks. This feature is designed for backup programs that need to be able to read everything on disk regardless of permissions.
This is not a security hole because the privilege SeBackupPrivilege which is required for this to work is by default granted to administrators only. Administrators, and in fact anyone with physical access to a machine, are always capable of taking control of and reading every file - unless it is encrypted.
As to which functions can be used to access files in backup mode: There is at least BackupRead for reading. Enumeration is easily possible with FindFirstFile/FindNextFile. Of course this requires the real Windows API, not the crippled .NET file system functions.

Windows 7 Compatibility Issue in .NET

When we create a SetUp & Deployment project for our application in .net, the default folder for our application to be installed is being set as C:\Program Files.....
Our application will run perfectly if we are using a Windows XP machine. But if we are using a Windows Vista or Windows 7 machine, the application wont run perfectly, especially if we are performing any file operations in our application...
Can anyone find a solution for this problem? Is there any means to penetrate this User Account Control and File Access Controls of Windows 7? or can any1 give a choice to change the default installation folder from [ProgramFilesFolder]\[Manufacturer]\[ProductName] to some other folder?
If your application writes to any files under its install folder (i.e. under Program Files if default path is used), then it is badly written. You shouldn't try to circumvent OS security mechanisms to protect the user from badly written apps; you should rather fix your app so that it works correctly.
And it is, of course, not a .NET issue at all. Any application doing the same thing, no matter which language/framework it's written in, will have the same problem.
You should still install your application in Program Files folder. there are good reasons to have it there - a single copy for all users, in a well known locked place where nobody but an admin can tamper with your binaries.
However, any file operation you are doing should be in one of the standard Windows locations for user-writable files. There are several such folders, depending on the file usage model. You can read more about these in the following SO questions :
My winform app uses xml files to store data, where should I store them so Vista users can write to them?
Vista and ProgramData
Data shared among all users should go in C:\ProgramData (use Environment.GetFolderPath(Environment.SpecialFolder.CommonApplicationData) to find out where it actually lives -- it can be different between Windows versions).
Data specific to the user should be in SpecialFolder.ApplicationData. If the user has a roaming profile, this is shared between machines.
Data specific to the user that's also specific to the machine should be in SpecialFolder.LocalApplicationData.
If you really need to put something in your program's installation directory, you need to do this with Administrator privileges.
You should either do this by prompting for elevation the first time that the program is run. Preferably, you should do this during installation (because you're already elevated).
First of all, you should not set your app to install under C:\Program Files\..., you should instead set it to %PROGRAMFILES%\... While these will usually equate to the same thing, they can be different on a 64 bit system, or they can be wildly different if the system has been set that way.
As already mentioned, don't try to circumvent the UAC, it is there for a reason, and your program is no more special than any other program on the system. Instead what you should do is set your app manifest to demand administrative level permission upon launch (which if granted bypasses the file system virtualization, although the user can decline it or possibly not even have the rights to launch something as admin). The other thing you can do is set the ACLs on the folder that your app sits in, and give all users on the machine read/write access to that folder (this would have to be done at install time).
Or you can do things the proper way and store your data files in the %APPDATA% folder, which you have full rights to, although these folders are specific to each individual user of the system.
I'd suggest start here http://channel9.msdn.com/pdc2008/PC51/
That will give you a good foundation.

Allow access permission to write in Program Files of Windows 7

My application throws 'Access denied' errors when writing temporary files in the installation directory where the executable resides. However it works perfectly well in Windows XP. How to provide access rights to Program Files directory in Windows 7?
EDIT:
How to make the program ask the user to elevate rights? (ie run program with full admin rights)
Your program should not write temporary files (or anything else for that matter) to the program directory. Any program should use %TEMP% for temporary files and %APPDATA% for user specific application data. This has been true since Windows 2000/XP so you should change your aplication.
The problem is not Windows 7.
You can ask for appdata folder path:
string dir = Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData);
or for TEMP path
string dir = Path.GetTempPath()
Your program has to run with Administrative Rights. You can't do this automatically with code, but you can request the user (in code) to elevate the rights of your program while it's running. There's a wiki on how to do this. Alternatively, any program can be run as administrator by right-clicking its icon and clicking "Run as administrator".
However, I wouldn't suggest doing this. It would be better to use something like this:
Environment.GetFolderPath(SpecialFolder.ApplicationData);
to get the AppData Folder path and create a folder there for your app. Then put the temp files there.
Options I can think of:
Run entire app as full admin priv. using UAC
Run a sub-process as full admin for only those things needing access
Write temporary files elsewhere
Add new item in the project: Application Manifest and save it.
Now open this file and look for <requestExecutionLevel>. It must be set to asInvoker.
Change it to highestAvailable. Now on executing your application, a prompt will appear asking for permission. Click yes!
Thats all :) now you can write and read from the system32 or any other file which requires admin right
You can verify your application by sigcheck.
sigcheck.exe -m yourapp.exe
And in the output check for element requestedExecutionLevel.
Another way round it would be to stop UAC then restart it. Create a CMD file with the following code;
Rem Stop UAC
%windir%\System32\reg.exe ADD HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System /v EnableLUA /t REG_DWORD /d 0 /f
rem force reboot
Start ShutDown /R /F /T 30
You'll need to right click on the CMD file and use run as admin. once you have finished what you are doing restart UAC with the following code (no need to use run as admin this time);
%windir%\System32\reg.exe ADD HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System /v EnableLUA /t REG_DWORD /d 1 /f
rem force reboot
Start ShutDown /R /F /T 30
The down sides to using this method is have to right click and use run as admin to close UAC down and you have to reboot for it to take effect.
BTW there are several reasons why you would need to write to the forbidden areas...the first two that springs to mind would be to run a batch file to append host to prevent your browser going to dodgy sites or to copy license keys in a silent install.
You can't cause a .Net application to elevate its own rights. It's simply not allowed. The best you can do is to specify elevated rights when you spawn another process. In this case you would have a two-stage application launch.
Stage 1 does nothing but prepare an elevated spawn using the System.Diagnostics.ProcessStartInfo object and the Start() call.
Stage 2 is the application running in an elevated state.
As mentioned above, though, you very rarely want to do this. And you certainly don't want to do it just so you can write temporary files into %programfiles%. Use this method only when you need to perform administrative actions like service start/stop, etc. Write your temporary files into a better place, as indicated in other answers here.
I cannot agree with arguments, that it is better to write all files in other directories, e.g., %APPDATA%, it is only that you cannot avoid it, if you want to avoid running application as administrator on Windows 7.
It would be much cleaner to keep all application specific data (e.g. ini files) in the same folder as the application (or in sub folders) as to speed the data all over the disk (%APPDATA%, registry and who knows where else). This is just Microsoft idea of clean programming. Than of course you need registry cleaner, disk cleaner, temporary file cleaner, ... instead of e+very clean practice - removing the application folder removes all application specific data (exep user data, which is normally somewhere in My Documents or so).
In my programs I would prefer to have ini files in application directory, however, I do not have them there, only because I cannot have them there (on Windows).
I think there is an alternate solution to all these problems....
Make an two level application. As said above...
1) Launcher which will launch another Main App using code such as (VB)
Call ShellExecute(hwnd, "runas", App.Path & "\MainApp.exe", 0, 0, vbNormalFocus)
2) Main App, which is writing to protected areas, ie Program Files folder
I've successfully tried this with windows 7
I'm also developing an app which has online update feature. But it doesn't work in Vista/W7..
I agree with other peoples about Microsoft Policies and Standard Practices.
But my Question is ..
1) How to apply update to an existing application, which probably always remain in Program Files folder.
2) There might be some way to do this, otherwise how goolge updater, antivirus updater or any software updater workes?
I need answer to my questions..... :o
Prof. Rajendra Khope
(MIT, Pune, India)
If you have such a program just install it in C:\, not in Program Files. I had a lot of problems when I was installing Android SDK. My problem got solved by installing it in C:\.
I was looking for answers. I found only one.
None of these work for me. I am not trying to write temporary files, unless this is defined as nonsystem files. Although I am designated the admin on my user profile, with full admin rights indicated in the UAC, I cannot write to program files or windows. This is very irritating.
I try to save an image found online directly to the windows/web/wallpaper folder and it won't let me. Instead, I must save it to my desktop (I REFUSE to navigate to "my documents/pictures/etc" as I refuse to USE such folders, I have my own directory tree thank you) then, from the desktop, cut and paste it to the windows/web/wallpaper folder. And you are telling me I should do that and smile? As an admin user, I SHOULD be able to save directly to its destination folder. My permissions in drive properties/security and in directory properties/security say I can write, but I can't. Not to program files, program files (86) and windows.
How about saving a file I just modified for a game in Program Files (86) (name of game) folder. It won't let me. I open the file to modify it, I can't save it without first either saving it to desktop etc as above, or opening the program which is used for modifying the file first as admin, which means first navigating all the way over to another part of the directory tree where I store those user mod programs, then within the program selecting to open file and navigate again to the file I could have just clicked on to modify in the first place from my projects folder, only to discover that this won't work either! It saves the file, but the file cannot be located. It is there, but invisible. The only solution is to save to desktop as above.
I shouldn't have to do all this as an admin user. However, if I use the true admin account all works fine. But I don't want to use the real admin account. I want to use a user account with admin rights. It says I have admin rights, but I don't.
And, finally, I refuse to store my portables in %appdata%. This is not how I wish to navigate through my directory tree. My personal installations which I use as portables are stored in the directory I create as a navigation preference.
So, here is the tried and true answer I have found:
From what I have seen so far.... unless one uses the real admin account, these permissions just aren't ever really available to any other user with admin privileges in the Windows Vista and Windows 7 OS's. While it was simple to set admin privileges in Windows XP, later versions have taken this away for all but those who can comfortably hack around.
While M$ "best practices" is to not write data into the %programfiles% folder; I sometimes do. I do not think it wise to write temporary files into such a folder; as the TEMP environment variable might e.g. point to a nice, fast, RAM drive.
I do not like to write data into %APPDATA% however. If windows gets so badly messed up that one needs to e.g. wipe it and reinstall totally, perhaps to a different drive, you might lose all your settings for nearly all your programs. I know. I've done it many times. If it is stored in %programfiles%, 1) it doesn't get lost if I e.g. have to re-install Windows on another drive, since a user can simply run the program from its directory, 2) it makes it portable, and 3) keeps programs and their data files together.
I got write access by having my installer, Inno Setup, create an empty file for my INI file, and gave it the users-modify setting in the [Files] section. I can now write it at will.
I am working on a program that saves its data properly to %APPDATA%, but sometimes, there are system-wide settings that affect all users. So in these situations, it HAS to write to the programs installation directory.
And as far as I have read now, it's impossible to temporarily get write access to one directory. You can only run the whole application as administrator (which should be out of the question) or not be able to save that file. (all or nothing)
I guess, I will just write the file to %APPDATA% and launch an external program that copies the file into the installation folder and have THAT program demand admin privileges... dumb idea, but seems to be the only practical solution...
You can add an access to IIS User for folders of Website or Web Application that you want write or rewrite in it.
It would be neater to create a folder named "c:\programs writable\" and put you app below that one. That way a jungle of low c-folders can be avoided.
The underlying trade-off is security versus ease-of-use. If you know what you are doing you want to be god on you own pc. If you must maintain healthy systems for your local anarchistic society, you may want to add some security.

Categories