Obviously you should assign ACLs such that users only have access to the minimum number of things they need to perform their tasks . Doing so is a bit trickier, however, and requires some planning. Also keep in mind that it is not just permissions on files and Registry keys that matter. You must also take into account permissions on shares, permissions within applications (such as a database management system), and so on. Particularly, share permissions seem to engender some debate. Our opinion is that there is usually nothing wrong with a share permission of Everyone full control. All that means is that the user will be allowed whatever access permissions are specified on the files and directories underneath the share. In other words, what it really means is "I do not want to manage permissions here." This was the default share permission until Windows Server 2003, where the default permission changed to read for Everyone. That means that unless you actually modify the permissions on a share, users cannot modify data on shares on Windows Server 2003. This has generated countless support calls, and we generally consider it a bad idea. It is confusing enough to manage permissions as it is without having to add the additional complexity of share permissions interacting with file system permissions into it. We recommend leaving the share permissions at Everyone full control. The only time we would not do that is if there is some reason a user should have fewer permissions on a file if he or she is accessing it remotely than the same user would have on that same file if he or she accessed it locally.
Whenever possible, assign permission for a resource to a group rather than individual users. Although there are many kinds of groups in Active Directory, for ACLs it is best to limit your choices to only a few. Use global groups to reflect roles or create membership based on business function or department location. This keeps replication traffic to a minimum  as you go through your daily tasks of modifying the members of these groups. Then on individual resources, use local groups to control access and add the appropriate global groups into the various local groups.
 Global groups do not replicate outside their own domain, and global catalogs list only the groups, not the members. Universal groups replicate everywhere in the forest, and global catalogs list all members.
The Built-In Shares
Windows includes a number of built-in shares. For instance, all fixed drives in the systems have a share denoted by the driver letter with a $ sign appended. For instance, there is a C$ share by default. There is also a share called Admin$, which maps to the %systemroot% directory (C:\Windows on most systems), as well as an IPC$ share used for interprocess communication, possibly a print$ share for printing, a netlogon share on domain controllers, and a few others depending on your system.
We have seen guidelines on securing the system that recommend changing the permissions on these shares. You cannot change the permissions on these shares . All except the IPC$ share are accessible only by administrators by default. The IPC$ share is accessible by anyone , but what you can do after you map it depends on what permissions you have to the objects it exposes, such as the Registry.
There are guidelines that recommend removing these shares. We do not like that idea much either. They are there for administration purposes. If you remove them, remote administration breaks. In addition, an attacker can easily add those shares back in should he need them, so removing them does not stop a competent attacker. Because only administrators can get to them by default, they are already pretty well locked down. If you want to protect them further, turn on the firewall and then set up an authenticated IPsec bypass, as discussed in Chapter 10, "Preventing Rogue Access Inside the Network," allowing only administrators to get to them. This is a much more usable and more secure option.
Be careful with "deny" ACEs. These override all other permissions, and it can be pretty easy to lock even an enterprise administrator out of a resource by, say, creating a "deny" ACE with Everyone as its member. Deny ACEs can prove useful, however, when you want to exclude a subset of a group that has permissions you do not want that subset to have or when you want to exclude a certain permission from groups you have granted full control to. However, use deny ACEs sparingly. Generally it is simpler to create a new group that contains the subset you want to give access to instead, for example. Deny ACEs confuse the security model and generally make the system more difficult to manage. Most people who have administered systems for awhile have funny stories about deny ACEs.
Once upon a time, when one of the authors still allowed his users to have local administrative privileges on their workstations, he received a phone call from one of them. The woman on the other end stated that her machine just suddenly decided to log her out and that it now will not allow her to log in any longer. When asked what she was doing at the time this happened , she replied, "Nothing, no, nothing, nothing at all." (That is known as a "hint" by the way.) I then asked what exactly it was she was not doing when the system logged her out. She said she was not changing any permissions. Exactly what permissions was she not changing? Well, she had discovered that Everyone had full control over her C: (which was the default up through Windows 2000). To rectify this situation, she changed that to deny Everyone full control instead. I asked whether she read the dialog box that popped up when she did so that states that deny ACEs take precedence over allow ACEs. She had clicked OK there. She also clicked OK on the following dialog box that said, in effect, "I do not think you heard me the first time. This is a bad idea." She clicked yes on that, too. She even clicked yes on the third dialog box that said, in effect, "OK, I will give you one more chance before you destroy your system. This is a really stupid thing to do, and you should click Cancel." After the propagation had proceeded far enough that she no longer had read access to any of the system binaries, the system decided to log her out. Fortunately, she did not reboot; had she done so, the system would not have booted . Since this was Windows NT 4.0, and before the "recovery console," that would most likely have meant flattening and rebuilding the box (because I felt no particular desire to take it apart and put the drive in another machine). As it were, the problem was resolved by mounting the C$ share from another system, taking ownership of the files in it, and then getting rid of the deny ACE. Of course, at this point, all the system-defined ACLs were lost, but at least she could now log on to the machine.
Inheritance, as we saw earlier, can be a tricky concept, but it is very useful. You should rely on inheritance to take care of most of your permission assignments. Whenever possible, assign permissions as high in the object tree as you can and configure branches and subtrees to use inheritance. Then, as necessary, add additional ACLs to fine-tune access control if the inherited ACL is too permissive or too restrictive .
Sometimes, however, a change or two makes some sense. For instance, Everyone has read access to the Domain Administrators group on a domain controller. There is usually no need for ordinary users to see this information, so consider removing access from everyone except members of the Domain Administrators. We have actually seen this done on production domains, and it makes things a bit more difficult for attackers if they cannot determine who the administrators are.
The effective permissions tool,  shown in Figure 17-3, in Windows XP and Windows Server 2003 can show you all the permissions that a certain user has on a particular object. To use it, open the properties on the object as if you were going to set permissions on it. Click the Security tab, and then click the Advanced button. Then click the Effective Permissions tab. Once there, click the Select button and pick a user. When you do, you get a dialog similar to what you see in Figure 17-3.
Often, it is very handy to list all the files (and Registry keys) that a user has access to. A product called SecurityExpressions from Pedestal Software  can help you learn a lot about who can do what with the resources across your network. The auditing capabilities of Security Expressions can check the current state of a machine and compare it against typical recommended configurations. SecurityExpressions includes a querying engine that can help you learn a number of things about the permissions and activities of your users:
Files or Registry keys that a particular user owns
Files or Registry keys created or modified during some time interval
All files or Registry keys a particular user can access
Files or Registry keys with unknown or deleted users in the ACL
Users with blank or expired passwords
Users who have not changed their passwords or are inactive
Users who have not logged in over some time period (or who never have)
Users who directly or indirectly belong to the Administrators group
Users with local log on rights to a server
Users with dial-in privileges
Groups with a specific, administrative, guest, or disabled member
Groups with identical memberships