tags:

views:

617

answers:

3

At my office, we have a network directory structure like this:

/jobs/2004/3999-job_name/...
/jobs/2004/4000-job_name/...

The issue is that employees rename the "4000-job_name" folders (which in turn breaks other things that rely on the name being consistent with a database).

How can I stop users from renaming the parent folder while still allowing them full control of that folder's contents?

Please keep in mind that this is a Samba share that Windows users will be accessing.

+6  A: 

I think you want that:

chmod a=rx /jobs     #chdir and lsdir allowed, modifying not
chmod a=rwx /jobs/*  #allow everything to everyone in the subdirectories

Since the directories /jobs/* are in fact files in /jobs their names cannot be changed without the write permission for /jobs. In the subdirectories of /jobs/ everyone one allowed to do everything with the commands above.

Be sure to set the permissions of new directories to rwx as you add them.

(edit by Bill K to fix the examples--the solution was correct but he misread the question due to the strange coloring SO added)

Johannes Weiß
If you can't modify /jobs/2004, doesn't that mean you can't add or delete a file from it?
Bill K
True, writing to /jobs/2004 is not allowed. Writing(e.g. creating/deleting/renaming a file) to /jobs/2004/* is allowed.
Johannes Weiß
I figured it out. You misread the problem a little. I'll fix...
Bill K
+2  A: 

The question has already been answered, so I'm just gonna make a brief remark: in your question, you use the terms "folder" and "directory" interchangeably. Those two are very different, and in my experience 99% of all problems with Unix permissions have to do with confusing the two. Remember: Unix has directories, not folders.


EDIT: a folder is two pieces of cardboard glued together, that contain files. So, a folder is a container, it actually physically contains the files it holds. So, obviously a file can only be in one container at a time. To rename a file, you not only need access to the folder, you also need access to the file. Same to delete a file.

A directory, OTOH, is itself a file. [This is, in fact, exactly how directories were implemented in older Unix filesystems: just regular files with a special flag, you could even open them up in an editor and change them.] It contains a list of mappings from name to location (think phone directory, or a large warehouse). [In Unix, these mappings are called links or hardlinks.] Since the directory only contains the names of the files, not the files themselves, the same file can be present in multiple directories under different names. To change the name of a file (or more precisely to change a name of a file, since it can have more than one), you only need write access to the directory, not the file. Same to delete a file. Well, actually, you can't delete a file, you can only delete an entry in the directory – there could still be other entries in other directories pointing to that file. [That's why the syscall/library function to delete a file is called unlink and not delete: because you just remove the link, not the file itself; the file gets automatically "garbage collected" if there are no more links pointing to it.]

That's why I believe the folder metaphor for Unix directories is wrong, and even dangerous. The number one security question on one of the Unix mailinglists I'm on, is "Why can A delete B's files, even though he doesn't have write access to them?" and the answer is, he only needs write access to the directory. So, because of the folder metaphor, people think that their files are safe, even if they are not. With the directory metaphor, it would be much easier to explain what's going on: if I want to delete you from my phonebook, I don't have to hunt you down and kill you, I just need a pencil!

Jörg W Mittag
Would you like to clarify?
Johan
I've worked with Linux professionally for over a decade. What is the difference exactly?
Matt Darby
uhhu, There is no difference. The reason folder is used is because that is the image someone chose to represent a directory. It also makes more sense to those less tech savvy.
he_the_great
@Johan, @Matt: Better? @he_the_great: take out a phonebook. Take out a folder. Place them side by side. Compare. Are they really the same?
Jörg W Mittag
To expand: I know that a lot of Unix UIs use folders to represent directories. That's precisely the point: it's wrong and it leads to misunderstandings. And misunderstandings when it comes to filesystem semantics often lead to either security breaches or data loss.
Jörg W Mittag
Another example: in OS/2, there was a shredder icon where Windows has a wastebin. The difference: if you put something in a shredder, it's gone, in a wastebin you can get it back out – which is precisely the different semantics these two features had.
Jörg W Mittag
I guess, what I am *really* trying to say is: if you choose a metaphor for your UI, choose wisely.
Jörg W Mittag
Got your point, and your angle is very interesting.
Johan
That is a good distinction at the implementation level, however at that level I don't know of anything that implements a 'folder' based file system. Which means that making a distinction is pointless, especially since usage is more representative as folders.
he_the_great
I disagree. Metaphors are important. Unix directories behave nothing like physical folders in real life do, but they behave at least somewhat like physical directories in real life. Using the wrong metaphor can lead to great confusion, and when it comes to filesystem semantics, great confusion ...
Jörg W Mittag
... often equals either data loss or security breaches.
Jörg W Mittag
+1  A: 

If you make the parent directory--/jobs/2004/--non-writable for the users, they won't be able to rename that folder.

I did the following experiment on my own machine to illustrate the point:

ndogg@seriallain:/tmp$ sudo mkdir jobs
ndogg@seriallain:/tmp$ sudo mkdir jobs/2004
ndogg@seriallain:/tmp$ sudo mkdir jobs/2004/3999-job_name/
ndogg@seriallain:/tmp$ cd jobs/2004/
ndogg@seriallain:/tmp/jobs/2004$ sudo chown ndogg.ndogg 3999-job_name/
ndogg@seriallain:/tmp/jobs/2004$ ls -alh
total 12K
drwxr-xr-x 3 root  root  4.0K 2009-03-13 18:23 .
drwxr-xr-x 3 root  root  4.0K 2009-03-13 18:23 ..
drwxr-xr-x 2 ndogg ndogg 4.0K 2009-03-13 18:23 3999-job_name
ndogg@seriallain:/tmp/jobs/2004$ touch 3999-job_name/foo
ndogg@seriallain:/tmp/jobs/2004$ mv 3999-job_name/ blah
mv: cannot move `3999-job_name/' to `blah': Permission denied
supercheetah