Is it possible to disable access of some program to files completely?
Because I don't want it to have any kind of access to files on system, is it possible to compile it so it doesn't have access to file stream or to run it someway it cant access files?
The closest you'd be able to come to that is to run your program in a chroot jail.
In an unmanaged environment, code cannot tell itself not to do something it shouldn't. CAS is part of managed environments only, where the runtime provides an extra level of access control. It's up to the OS to prevent applications from doing things that the user they are running on behalf of cannot do. You should be able to run the application as if you were a different, more limited user; then, you could limit the user's access rights to the resource and the OS will prevent the code from accessing it.
In Linux, you can change the owner of the process to nobody. This is no big security increase, as nobody still can access files etc. but it's better than running as a local user or root:
struct passwd *pw = getpwnam("nobody");
if (!pw)
printf("Error: Unable to look up info about user nobody");
else{
setuid(pw->pw_uid);
setgid(pw->pw_gid);
}
In theory you can direct the linker not to link fopen and so on. You'll probably have to use static linkage.
But, often, when you come to a requirement like this you're approaching the problem from the wrong direction. What is it you are trying to achieve with this hack? Why do you want this?
Under Windows, you can start the process under a restricted token
This requires more than just a basic knowledge of Windows API, but it's possible.
Related
I am developing an application for a small office to maintain their monetary accounts.
My application can help create a file which can store all the information.
But it should not be accessible to the user other than in my application.
Why? Because somebody may delete the file & all the records will vanish.
The environment is a Windows PC with a single account having admin privilages.
I am developing the application in C++ using the MinGW compiler.
I am sort of blank right now, as to how I can create such a file.
Any suggestions please?
If your application can modify it, then the user under whose credentials it runs can modify it, period. Also, if he has administrator privileges then you can't stop him from deleting stuff, even if your application runs under different credentials and the file is protected by ACLs.
Now, since the problem seems to be not of security, but of protecting the user from himself, I would just store the file in a location that is "out of sight" enough and be happy with it; write your data in %APPDATA%\yourappname1, such a directory is specifically for user-specific application data that is not intended to be touched directly by the user.
If you want to be paranoid you can enable every security setting you can find (hide the directory, protect it with a restrictive ACL when the app is not running, open it for exclusive access, ...), but if you ask me it's just wasted time:
the average user (our target AFAICT) doesn't mess in appdata, since it's a hidden folder to begin with;
the "power user" who messes around, if sufficiently determined to shoot himself in the foot (or voluntarily do damage), will find a way, since the security settings are easily circumventable in your situation (an admin can take ownership of any file and change its ACLs, and use applications like Unlocker to circumvent file locking);
the technician that has legitimate reasons to access the file (e.g. he must take/restore a backup of it) will be frustrated by all these useless precautions.
You can get the actual %APPDATA% path by expanding the corresponding environment variable or via SHGetFolderPath/SHGetKnownFolderPath (or whatever replacement they invented for it in new Windows versions).
Make sure your application loads on windows boot and opens the file with dwShareMode 0 option.
Here is an MSDN Example
You would need to give these files their own file extension and perhaps other security measures (I.e passwords to files). If you want these files to be suggested by Windows then you will have to do some work with the registry.
Here's a good source since you're concerned with Windows only:
http://msdn.microsoft.com/en-us/library/windows/desktop/ff513920(v=vs.85).aspx
As far as keeping the data from being deleted, redundancy my friend redundancy. Talk to a network administrator about how they keep their data safe. I'd bet money on them naming lot's of backups as one of their reasons.
But it should not be accessible to the user other than in my application.
You cannot do that.
Everything that exists on machine user has physical access to can be deleted if user has sufficient determination.
You can protect your file from being deleted while program is running - on windows, you can't delete open files. Keep file open, people won't delete it while your program is running. Instead, they will kill your program via task manager and delete the file anyway.
Either that, or you could upload it somewhere. Data that is not located on physically accessible device cannot be easily deleted by user. However, somebody will have to run the server (and deal with security + possibly write server software). In your case it might not be worth it.
I'd suggest to document location of user data in help file, and you should probably put "!do not delete this.txt" or something into folder with this file.
How do you set a program to ask for elevation upon execution? I've asked around here and there, but haven't gotten an answer. I'm not sure how I would do this, but the program that i want to write, needs permissions to be run.
Security models are rather platform-specific. Qt does not AFAIK address this sort of thing. (Case in point: the Qt Creator installer itself choked when I didn't run it as root.)
You'll presumably need to make native calls or interact with some daemon designed for the purpose. Often easiest to try whatever it is you think you should be able to do, and check for failure, and if you can't do what you want then ask the user to explicitly re-run with higher privileges.
Linux:
Best way elevate the privileges programmatically under different versions of Linux?
Windows:
http://msdn.microsoft.com/en-us/magazine/cc163486.aspx
Mac:
Escalate App Privileges Programmatically OS X
(Note: Often if you have to ask a question about something like this, there may be a better way to do whatever it is you're trying to do. Consider posting a question that is more general about what you want, and you might get suggestions on a way to do it more cleanly.)
I don't think it is possible to ask to be elevated automatically.
The only way I can think of doing it would be to have a service running as a Local Administrator account and performing elevated run for you.
I have used this when installing/uninstalling MSI packages autmatically as part of a CI Build (Go Agent runs as Local System Account)
Our app is ran from SU or normal user. We have a library we have connected to our project. In that library there is a function we want to call. We have a folder called notRestricted in the directory where we run application from. We have created a new thread. We want to limit access of the thread to file system. What we want to do is simple - call that function but limit its access to write only to that folder (we prefer to let it read from anywhere app can read from).
Update:
So I see that there is no way to disable only one thread from all FS but one folder...
I read your propositions dear SO users and posted some kind of analog to this question here so in there thay gave us a link to sandbox with not a bad api, but I do not really know if it would work on anething but GentOS (but any way such script looks quite intresting in case of using Boost.Process command line to run it and than run desired ex-thread (which migrated to seprate application=)).
There isn't really any way you can prevent a single thread, because its in the same process space as you are, except for hacking methods like function hooking to detect any kind of file system access.
Perhaps you might like to rethink how you're implementing your application - having native untrusted code run as su isn't exactly a good idea. Perhaps use another process and communicate via. RPC, or use a interpreted language that you can check against at run time.
In my opinion, the best strategy would be:
Don't run this code in a different thread, but run it in a different process.
When you create this process (after the fork but before any call to execve), use chroot to change the root of the filesystem.
This will give you some good isolation... However doing so will make your code require root... Don't run the child process as root since root can trivially work around this.
Inject a replacement for open(2) that checks the arguments and returns -EACCES as appropriate.
This doesn't sound like the right thing to do. If you think about it, what you are trying to prevent is a problem well known to the computer games industry. The most common approach to deal with this problem is simply encoding or encrypting the data you don't want others to have access to, in such a way that only you know how to read/understand it.
Whats the best way to add a user/group in linux using C++ is there a library I can call on? I dont want to start doing things like:
fopen("/etc/passwd", "a");
fprintf(tmp, "%s:x:%d:1:%s:/%s/%s:/bin/ksh\n", username, usernumber, commentfield, userdir, username);
fclose(tmp);
fopen("/etc/shadow", "a");
fprintf(stmp, "%s:*LK*:::::::\n", username);
fclose(stmp);
Thanks!
I've noticed that most major utilities that add and change users do so directly, often in different ways. The functions you can use to modify the passwd and shadow files are exposed in <pwd.h> and in <sys/types.h>, and they're part of glibc.
fgetpwent, getpwnam, getpw, getpwent_r, putpwent, setpwent
We can look into how busybox (via TinyLogin) does it, as an example. In busybox/loginutils/adduser.c, they put a user in the passwd file by building the passwd structure and then call putpwent. For adding the user's password in the shadow file, they simply call fprintf and write the string directly.
For authenticating users the modern way, there's Linux-PAM. But as far as adding users, you can see in pam_unix_passwd.c that they call unix_update_db(), which calls various functions in libpwdb, which you'd have to add as a dependency to your project if you use it.
That being said, I'm guilty of having written a couple utilities to parse the passwd and shadow databases and modify them directly. It worked fine, but this was on an embedded system where I could tightly control everything. I didn't have to worry about things like race conditions with other programs modifying the passwd db.
If you need to add a group, same goes for the group database.
You might try using the libuser library.
One of the applications that are distributed with libuser is luseradd, a program that appears to be a cross-platform useradd utility. At its core, luseradd uses libuser's lu_user_add function to physically create the user.
See the docs/html folder in the source distribution for documentation.
Adding a user is a bit too high-level for there to be a system call for it. As far as I'm aware, there aren't any widely used libraries for this either. Your best bet will probably be to use the system call to invoke the useradd program with appropriate options.
I want to access a file on remote machine(win2k3, 10.10.20.30), but i couldn't understand how to login to that machine in my program. is there any simple win api that takes network path, credentials and returns the handle?
i just want to access \10.10.20.30\c$\test.txt,
WNetAddConnection2, WNetAddConnection3 are little confusing. Any suggestion will be helpful.
sorry for not being very clear. I want to access a computer on same network(LAN).
I wanted to access a file that is not shared on other computer.
If you have administrator rights, the solution is fairly simple. The C$ administrative share is available. You can call WNetAddConnection2 to create a local driveletter pointing to it. NETRESOURCE.dwType = RESOURCETYPE_DISK of course, .lpLocalName = NULL as you don't need it, .lpRemoteName = _T("\\\\10.10.20.30\\c$") (note the escaping of \ in C strings, it really starts with 4 of them). .lpProvider = NULL - let Windows figure the provider out.
Leave the username/password empty, and Windows will use your current user credentials. If those are indeed (network) administrator credentials, they're sufficient.
dwFlags should include CONNECT_TEMPORARY, as you're only interested in one file.
However, I think that (given sufficient credentials) it's easier to just call CreateFile("\\\\10.10.20.30\\c$\\test.txt") and let Windows deal with the details.
Normal c++ file access functions and libraries should work as is, just put the full network path to the file where you would put the file name, and you should be able to access. Good tutorials with sample code available at this link: http://www.cplusplus.com/doc/tutorial/files/
If you are getting errors, check that the user you are logged in as has file permissions set on the shared folder, as well as sharing permissions.
Execute mstsc.exe from your code using createprocess... Rest of thing it will handle...