Low Disk Space Alert Script

If backups should fail, or there is a mail storm…
How can I get alerted when the Exchange database transaction log disk is almost full?
It’s not a good day when the database dismounts because the TL disk fills up.
The info below is a script that will email you an alert when the TL disk gets under 10%

When a logical drive gets to 10% free (DiskSpaceThreshold) or 400MB left (LowDiskSpaceMinimum), the system log has an event ID 2013 generated.
These are defaults built into the OS.
If you want to change either of these settings, you have to create the registry key.

I assume you don’t have an enterprise program such as SCOM that monitors events… well then this powershell script is for you.
I created a task in task scheduler. I called it “LowDiskSpaceEventID2013”. I manually ran it to make sure it works properly, hence the last run time. (I had it send email to me while testing)

We probably want to change who it runs as, like a service account….

If I click on “Edit”, it has these properties

I put the script in the D:\WorkingFiles folder, the script is called SendMail.ps1. See the attached file.
The powershell script that can email someone internally.
If I point the server to itself when sending out, I get this error

The whole script looks like this

#SMTP server name
$smtpServer = "ex02.domain.local"
#Creating a Mail object
$msg = new-object Net.Mail.MailMessage
#Creating SMTP server object
$smtp = new-object Net.Mail.SmtpClient($smtpserver)
#Email structure
$msg.From = "no-reply@yourdomain.com"
$msg.ReplyTo = "no-reply@yourdomain.com"
$msg.subject = "Low Disk Space on EX01"
$msg.body = "Event ID 2013 has been generated on EX01. Disk space is below 10% or 400MB"
#$msg.IsBodyHTML = $true
#$msg.body = get-content .moves.htm
#Sending email

I exported the task to an xml file.
Then I imported this task on the other exchange servers.
I copied the script and modified it for each server

The email message looks like this:


Testing Open Relay / Allowed Relay using PowerShell

In my previous post, I posted a script which emails me move reports from office 365. A subset of that script emails using a non-authenticated connection.  This code allows you to test an open relay too… In many ways much easier than using Telnet. So here is that code again. 

     #SMTP server name
      $smtpServer = "relay.domain.com"
     #Creating a Mail object
      $msg = new-object Net.Mail.MailMessage
     #Creating SMTP server object
      $smtp = new-object Net.Mail.SmtpClient($smtpServer)
     #Email structure 
      $msg.From = "no-reply@domain.com"
      $msg.ReplyTo = "no-reply@domain.com"
      $msg.subject = "subject"
      $msg.IsBodyHTML = $false
      $msg.body = "Hello world, testing relay"
     #Sending email 

SPF ending “all” word explained

While creating a SPF record on Microsoft’s wizard, I noticed this question

Does {your email domain} send e-mail from any IP addresses that are not identified in the above sections?

There are several radio button options.

  • Yes; mail may legitimately originate from IP addresses not identified above.
  • No; this domain sends mail only from the IP addresses identified above.
  • Neutral; this domain makes no statement about whether mail may legitimately originate from IP addresses not identified above.
  • Discouraged; mail may legitimately originate from IP addresses not identified above, however, use of such IP addresses is discouraged and may not be permitted in the future.

At the end of the spf record there is the word “all”, for example my spf record is this:

v=spf1 include:spf.protection.outlook.com ~all

See the ~all at the end?

There are other options, each corresponding to the options above.

Yes is +all

No is  -all

Neutral is ?all

Discouraged is ~all

http to https redirect Windows 2008 IIS

This is the best way I have found to redirect http to https and to a specific sub url.

Hence if the user types mail.uwhpwatertown.com, which implies http, they will, thru IIS error handling, get redirected to https://mail.whatever.com/owa

I was doing this for a client, and I took some screenshots to make it easier to understand.

It’s a good solution for OWA and probably for other websites as well.

Step ONE:

change the error setting.

Go to the Default Web Site in IIS managment, click the error pages button

On the far right, click the “Edit Features Settings…”

Change the settings from the bottom radio button….


That gives you this error ……

To this setting

Which gives you this setting

Step two:

Click on this 403 error (403 means you hit the web page with http, when it requires https)

Change it from this:

To this


Click ok, now it should look like this:


Test it by typing mail.whatever.com, or localhost (at the server), you will get redirected to https://mail.whatever.com/owa

So, in summary, that covers http to https redirect (with additional redirect to /owa)

But what about if someone types https://mail.whatever.com , meaning they typed https, but did NOT include the /owa at the end.

We need that to redirect to the /owa subfolder.

In the root of the web server, add a file called default.htm and add the following text at the contents of that default.htm

Change the FQDN to your appropriate address.

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">

<HTML dir=ltr>
  	Do Not Change anything in the <HEAD> section except the data in the
  	"META http-refresh" tag or you may render this page non-functional
  <TITLE>The page cannot be displayed</TITLE>
  <META content=NOINDEX name=ROBOTS>
  <META http-equiv=Content-Type content="text-html; charset=Windows-1252">
  	Using the following META-tag, we instruct the browser to automatically seek another page.
  	http-equiv="Refresh" instructs the browser to refresh its content
  	content= has two parts:
  		0 = time delay in seconds before the browser actually executes the redirection
  	 	URL = the actual content to seek
  	With the given settings, the browser will seek "URL" immediately
  <META http-equiv="Refresh" content="0;URL=https://FQDN/owa">
  <META content="MSHTML 5.50.4522.1800" name=GENERATOR>

Import Export IP list on Allowed Relay Receive Connector

If you are migrating from Exchange 2003 to 2010, when you export the list of allowed relay devices, following this article http://support.microsoft.com/kb/935635 the output will typically be in this format:

Name the file IPList.txt
So, with the script below, you can import the list of ip addresses on your receive connector

$RecvConn = Get-ReceiveConnector "Ex2010\AllowedRelay"
Get-Content .\IPList.txt | foreach {$RecvConn.RemoteIPRanges += "$_"}
Set-ReceiveConnector "Relay Connector" -RemoteIPRanges $RecvConn.RemoteIPRanges

When you are migrating from Exchange 2007 to 2010, we use powershell command to export the list, and a powershell script to import

Here is the powershell command to export the list. Change the exchange 2007\allowedrelay part to be the correct server\receive connector name.

(Get-ReceiveConnector "exchange2007\allowedrelay").RemoteIPRanges | select Lowerbound,Upperbound,RangeFormat | sort-object Lowerbound| export-csv c:\rc.txt –NoTypeInformation

Use this script to import it onto the exchange 2010, change the second line to be the correct exchange 2010 server name \ receive connector name

$csv = "c:\rc.txt"
$rc = "EX2010\RelayConnector"
$impcsv = import-csv $csv
foreach($line in $impcsv)
$ipAdd = $line.LowerBound
$conn = Get-ReceiveConnector $rc
$conn.RemoteIPRanges += $ipAdd
Set-ReceiveConnector $rc -RemoteIPRanges $Conn.RemoteIPRanges

Folder and File level scanning Exclusions for Exchange 2010

There is a technet article

Titled : File-Level Antivirus Scanning on Exchange 2010
Please read the first section to understand the requirements.

To make the rest of the article easier to understand, as it does get a bit convoluted after the introduction….

The following folders (and subsequent subfolders) need exclusions:

C:\Program Files\Microsoft\Exchange Server\V14\Mailbox
C:\Program Files\Microsoft\Exchange Server\V14\GroupMetrics
C:\Program Files\Microsoft\Exchange Server\V14\TransportRoles
C:\Program Files\Microsoft\Exchange Server\V14\Logging
C:\Program Files\Microsoft\Exchange Server\V14\ExchangeOAB
C:\Program Files\Microsoft\Exchange Server\V14\Mailbox\MDBTEMP
C:\Program Files\Microsoft\Exchange Server\V14\Working\OleConvertor
C:\Program Files\Microsoft\Exchange Server\V14\ClientAccess


C:\inetpub\temp\IIS Temporary Compressed Files

In my deployment, I typically  put the Transaction logs on E and databases on F


In addition, as mentioned in the article,
Many file-level scanners now support the scanning of processes, which can adversely affect Microsoft Exchange if the incorrect processes are scanned.
Therefore, you should exclude the following processes from file-level scanners.
(I re-sorted the table from the technet article into alphabetical listing for easy reading)

In addition to excluding specific directories and processes, you should exclude the following Exchange-specific file name extensions in case directory exclusions fail or files are moved from their default locations.

Application-related extensions

Database-related extensions

Offline address book-related extensions:

Content Index-related extensions

Exchange 2007 /2010 Certificate install

Exchange 2007 /2010 installs itself with a self signed certificate. This means it gets you going with ssl, but it’s not something you want to run with in production. Why? Well, workstations accessing OWA will complain with a popup box saying it isn’t trusted, and SMTP attempting TLS won’t work because the receiving side (something on the internet) won’t trust it. It’s self signed.

So the first thing we need to do is generate a certificate request. This is generated using Exchange powershell, not IIS. Why? IIS does not have the ability to generate an SSL request with SANs. SANs?, Subject Alternative Names, are other names within the certificate besides the normal name, which is called the CN (Common Name).

Typically, an exchange server needs three names:

The first one is for Outlook 2007/2010 users to autoconfigure the client when they are external to the network. An outlook client will user this address to read an xml file off the server to configure the client to user outlook anywhere (rpc over https) to connect.
The name “autoconfigure” is hardcoded into outlook. The external domain in this case is the domain that the user would use for their email. So if the person’s email was madengineer@whatever.com, the name would be autodiscover.whatever.com

The second one is for Outlook Web Access. I typically use this for the Common Name also. Some companies use “webmail”, some use “mail”, and some use “owa”. I like webmail.

The third is the server’s FQDN with “internaldomain.local” referencing the active directory domain name.  You need this name or outlook clients will complain every time they connect. Why? Because Outlook 2007/2010 use a secure connection to the Exchange server, whereas Outlook 2003 does not.

Now, how to generate the code for this? It’s really simple if you go to this site for Exchange 2007 and this site for Exchange 2010 and fill out the info . Remember to include your common name in the first san field also. It may seem redundant, but it’s not.


In my example, the code for 2007 is this:

New-ExchangeCertificate -GenerateRequest -Path c:\certs\webmail_externaldomain_com.csr -KeySize 2048 -SubjectName "c=US, s=Wisconsin, l=Madison, o=Company, ou=IT, cn=webmail.externaldomain.com" -DomainName webmail.externaldomain.com, autodiscover.exernaldomain.com, servername.internaldomain.com, servername -PrivateKeyExportable $True

For convenience I make a folder off the C drive called Certs, then i place the above text in a text file called commands-used.txt or something like that. That way I can go back to it.

After you generate the file, c:\certs\webmail_exernaldomain_com.csr, you need to submit it the the certificate authority. I like to use Digicert.com because they have the best price on a 4 name san certificate. BTW, these are also called a “unified communications” certificate.
You will get back another file from digicert.com that is the other half of this certificate.

Download this file, which will end in .cer to the root of the c: drive. Let’s call it newcert.cer for sake of discussion.

Then use the following powershell command to install the certificate.

For Exchange 2007 type:

Import-ExchangeCertificate -Path C:\newcert.cer

You will see it echo back the thumbprint of the certificate, highlight the thumprint and put it in the clipboard.

For Exchange 2010 type:

Import-ExchangeCertificate -FileData ([Byte[]]$(Get-Content -Path c:\certs\your_domain_name.cer -Encoding byte -ReadCount 0)) 

For both version of Exchange, the command to enable the certificate is:

Enable-ExchangeCertificate -Thumbprint xyxxyxyxyxy -Services SMTP, IIS

Where the xyx… is the thumbprint you put in clipboard.

Test it by accessing owa, https://servername.internaldns.local/owa on the server and viewing the certificate in the browser.

You can also test it by performing a telnet to the server’s ip address, port 25 and issue a starttls command.

That’s pretty much it for the cert generation. You can delete the private self generated cert if you want. The biggest problem people run into is the powershell code.