Shared Hosting with Exchange 2007 (Part 2)


If you missed the other parts in this article series please read:

Hiding Address Lists

This is really the tricky part of a hosting solution with Exchange 2007. Exchange Server 2007 scales very well to thousands of mail enabled objects, so it’s not a question of size. The difficult part is isolating each hosted organization in order to give them a user experience as if they were the only organization on the server.

What we did in Part 1 of this article was to create different address lists and to assign each mail enabled object its own e-mail address policy. If we did nothing else, the user would see everyone else hosted on the server when he or she used Outlook (Figure 1). The desired scenario is a complete isolation of the address lists. We want our Maxwell Smart to only see the other CONTROL Agents, as illustrated in Figure 2.

And how do we accomplish this? By playing around with ADSI Edit and ACLs and using some non-standard procedures that Microsoft neither recommends nor supports. But since I’m writing for academic purposes, I’ll show you how.


Figure
1


Figure
2

Active Directory Object Permissions Quick Tutorial

The most common read permissions (List Contents, Read All Properties, and Read Permissions) are usually enough to cover most scenarios, but for our slightly advanced configuration we’ll need to use a less known permission: List Object. Figure 3, taken from ADSI Edit, illustrates the advanced security properties of an Active Directory object.


Figure
3

To enable the List Object functionality, you must modify the dSHeuristics property (using ADSI Edit,) of the object CN=Directory Service, CN=Windows NT, CN=Services, CN=Configuration, DC=mydomain, DC=local (Figure 4). The property uses string syntax and by default the value is not set, but its internal default is 0. The dSHeuristics is a Unicode string in which each character contains a value for a single domain-wide setting. The third character from left controls the List Object functionality. In other words, to enable it, you must write 001 into the dSHeuristics property (Figure 5).


Figure
4


Figure
5

While the List Contents permission allows viewing of all immediate child objects, using List Object allows hiding some of them. If someone doesn’t have List Contents to the parent object, List Object can be used to grant him permission to see the existence of individual child objects. That user sees only those child objects for which he has the List Object permission and the remaining child objects are invisible to him.

Note:
For the List Object permission to work, you must grant it also for the parent object. Consequently, you must block permission inheritance of those child objects that you want to make invisible by removing List Object from them. Modifying the dsHeuristics property can greatly increase the number of access check calls that are made, and can have a significant negative effect on performance.

For more information on this subject, please read Controlling Object Visibility.

Modifying Permissions for the Address Lists Containers

WARNING!:
THE FOLLOWING PROCEDURES ARE NEITHER SUPPORTED NOR RECOMMENDED BY MICROSOFT!

We’ll use ADSI Edit from the Windows 2003 Support Tools to tweak the permissions of the Address Lists containers (All Global Address Lists, All Address Lists and the Offline Address Lists) and sub containers.

The procedure consists of the following steps:

Containers

  • Remove Permissions Inheritance for All Address Lists, All Global Address Lists, Offline Address Lists;
  • In the Security tab, remove the Anonymous Logon, Everyone and Authenticated Users;
  • Add Authenticated Users and grant them List object so they can access the folders below containing their own address lists (using PowerShell).

Address Lists

  • Remove Permissions Inheritance for each Address List, GAL and OAB we created;
  • Remove Authenticated Users from the Security tab;
  • Add the appropriate permissions for each list, so that only one organization can read them.

  1. So, let’s start by running ADSI Edit, expand Configuration | CN=Configuration,DC=mydomain,DC=local | CN=Services | CN=Microsoft Exchange | CN=My Organization | CN=Address Lists Container, right click CN=All Address Lists and select Properties (Figure 6).


Figure
6

  1. Go to the Security tab, click Advanced and deselect Allow inheritable permissions from the parent to propagate to this object… (Figure 7). After clicking OK, select Copy on the Security warning (Figure 8). Some other warnings will pop up, select Yes in all of them (Figure 9, Figure 10).


Figure
7


Figure
8


Figure
9


Figure
10

  1. Back at the Security tab, remove the Anonymous Logon, Everyone and Authenticated Users and click OK.
  2. Repeat steps 1-3 for All Global Address Lists and Offline Address Lists.
  3. Add the List Object permission for Authenticated Users. In order to automate this task, let’s use some PowerShell commands (Figure 11):
    $container = “CN=All Global Address Lists,CN=Address Lists Container,CN=My Organization,CN=Microsoft Exchange,CN=Services,CN=Configuration,DC=mydomain,DC=local”
    Add-ADPermission -Identity $container -User “Authenticated Users” -AccessRights ListObject
    $container = “CN=All Address Lists,CN=Address Lists Container,CN=My Organization,CN=Microsoft Exchange,CN=Services,CN=Configuration,DC=mydomain,DC=local”
    Add-ADPermission -Identity $container -User “Authenticated Users” -AccessRights ListObject
    $container = “CN=Offline Address Lists,CN=Address Lists Container,CN=My Organization,CN=Microsoft Exchange,CN=Services,CN=Configuration,DC=mydomain,DC=local”
    Add-ADPermission -Identity $container -User “Authenticated Users” -AccessRights ListObject


Figure
11

  1. Let’s move on to the lists we previously created. Repeat steps 1-2 for each Address List, Global Address List and Offline Address List created for our spy agencies.
  2. For each of the previously mentioned lists, remove Authenticated Users from the Security tab.
  3. Add appropriate permissions for each list, so that only one organization can read its own list. We can use the following PowerShell commands (Figure 12):
    $container = “CN=KAOS GAL,CN=All Global Address Lists,CN=Address Lists Container,CN=My Organization,CN=Microsoft Exchange,CN=Services,CN=Configuration,DC=mydomain,DC=local”
    Add-ADPermission $container -User “KAOS Agents” -AccessRights GenericRead, ListChildren -ExtendedRights Open-Address-Book
    $container = “CN=KAOS AL,CN=All Address Lists,CN=Address Lists Container,CN=My Organization,CN=Microsoft Exchange,CN=Services,CN=Configuration,DC=mydomain,DC=local”
    Add-ADPermission $container -User “KAOS Agents” -AccessRights GenericRead, ListChildren -ExtendedRights Open-Address-Book
    $container = “CN=KAOS OAB,CN=Offline Address Lists,CN=Address Lists Container,CN=My Organization,CN=Microsoft Exchange,CN=Services,CN=Configuration,DC=mydomain,DC=local”
    Add-ADPermission $container -User “KAOS Agents” -AccessRights GenericRead, ListChildren -ExtendedRights ms-Exch-Download-OAB


Figure
12

Additional Active Directory Tweaks

With the right permissions in place, the correct Global Address List for each hosted company will be displayed. But for the general Address List and Offline Address Book, further Active Directory tweaking is necessary.

For the Address Lists, we must add each distinguished name to the addressBookRoots attribute of CN=Microsoft Exchange, CN=Services, CN=Configuration, DC=mydomain, DC=local.

In order to do this, we can edit the properties of each address list and copy the distinguishedName attribute value (Figure 13). Next, right click CN=Microsoft Exchange, select Properties (Figure 14) and add the previously copied value to addressBookRoots. Repeat these steps for each address list. Figure 15 depicts all the address book roots that Exchange will use (All Address Lists, CONTROL AL and KAOS AL).

WARNING!
If you experience OAB creation/replication problems after this step, please read this post: Exchange Shared Hosting and addressBookRoots.


Figure
13


Figure
14


Figure
15

As for Offline Address Books, since we use multiple OABs, we must determine which users download which OAB. There are three ways to specify that:

  • Per-Mailbox Database: By using the Exchange Management Console or the Exchange Management Shell, you can specify the public folder database and the OAB that recipients download by linking the OAB to the mailbox database.
  • Per-Recipient: By using the Set-Mailbox cmdlet in the Exchange Management Shell, you can specify which OAB recipients will download by linking the OAB to the recipient’s mailbox.
  • Per Multiple Recipients: By using a pipelined command in the Exchange Management Shell, you can specify multiple OAB recipients to download a specific OAB based on common attributes.

For our hosted scenario, there’s no specific requirement to separate the different organizations in different Database stores. Nevertheless, I would say that it would be a best practice. In this case, we can determine the specific OAB by using EMC. Expand Server Configuration, select Mailbox, right click the database store you want to modify and select Properties. Go to the Client Settings tab and Browse the desired OAB (Figure 16). Click OK.


Figure
16

If you prefer, we can use multiple recipient filtering and set the OAB with PowerShell:

Get-User -Filter { userPrincipalName -like “*@control.org” } | Set-Mailbox -OfflineAddressBook “CONTROL OAB”

Get-User -Filter { userPrincipalName -like “*@kaos.org” } | Set-Mailbox -OfflineAddressBook “KAOS OAB”

After using either method (EMC or PowerShell), you can check the attributes of one of our secret agents and see that the msExchUseOAB value points to the right Offline Address Book (Figure 17).


Figure
17

We could also have used ADModify.NET to perform the attribute change. We’ll use this tool a little bit ahead to illustrate its potentials.

Our last AD tweak is necessary to restrict OWA address view searches. In Outlook Web Access, you can view all address lists in Active Directory, regardless of the permissions that are set on the address list. Without this restriction, all users could see everyone else’s address lists, as depicted in Figure 18.


Figure
18

To restrict access so that OWA users can only view the address lists for which they have permission, you can configure the msExchQueryBaseDN attribute for the OWA user.

This time we’ll use ADModify.NET. Start by running this tool and clicking Modify Attributes (Figure 19).


Figure
19

From the drop down list, select a domain and a domain controller and click the big green button. This will add the domain to the lower pane, which you must expand by double clicking it. Select the OU that contains your users and click Add To List. The users will be displayed in the right pane (Figure 20). Click Next.


Figure
20

Select the Exchange General tab and modify the attributes you want (Figure 21). For Control Agents we want to limit the OWA address list search to their own OU, so the value of msExchQueryBaseDN will be OU=CONTROL,OU=Hosting,DC=mydomain,DC=local. Note that this could also have been used to modify msExchUseOAB.


Figure
21

Summary

This second part of Shared Hosting with Exchange 2007 is not for the faint of the heart. We dealt with some pretty advanced Active Directory tweaking. The incorrect use of tools such as ADSIEdit can cause serious problems to the whole AD forest. Use it with caution and always have a backup plan.

On the next and final part of this article we’ll set up some side features, such as Public Folders, and finally test the whole solution.

Additional Links

If you missed the other parts in this article series please read:

About The Author

Leave a Comment

Your email address will not be published. Required fields are marked *

This site is protected by reCAPTCHA and the Google Privacy Policy and Terms of Service apply.

Scroll to Top