Use TLS/SSL with POP3 in .NET

Mail.dll POP3 .NET email component supports Secure Socket Layer (SSL) and Transport Layer Security (TLS) protocols to authenticate the server and secure client-server email downloads.

There are two modes in which Mail.dll can work:

  • Implicit – where Mail.dll POP3 client immediately connects using secure channel,
  • Explicit – where Mail.dll POP3 client connects on unsecured channel first and then secures the communication by issuing STLS command. This mode is sometimes called TLS.

In both cases, by default, Secure Sockets Layer (SSL) 3.0 and Transport Layer Security (TLS) 1.0, 1.1, 1.2, 1.3 are acceptable for secure communication. You can change the defaults using Pop3.SSLConfiguration property.

Pop3 client may decide to secure the channel, if POP3 server explicitly forbids logging-in on unsecured channel and you are using UseBestLogin method.

Here you can find more details on SSL vs TLS vs STARTTLS.

POP3 implicit TLS/SSL mode

Mail.dll POP3 component connects using secure TLS/SSL channel. You need to know in advance, if the server supports TLS/SSL connections – ask your administrator. Typically, POP3 over TLS/SSL is associated with port 995, but this is not always the case. You can always specify different, then standard port, using ConnectSSL method overloads.

// C# version

using System;
using Limilabs.Mail;
using Limilabs.Client.POP3;

class Program
{
    static void Main(string[] args)
    {
        using (Pop3 pop3 = new Pop3())
        {
            pop3.ConnectSSL("pop.example.com");
            pop3.UseBestLogin("user", "password");

            MailBuilder builder = new MailBuilder();
            foreach (string uid in pop3.GetAll())
            {
                var eml = pop3.GetMessageByUID(uid);
                IMail email = builder.CreateFromEml(eml);

                string subject = email.Subject;
            }
            pop3.Close();
        }
    }
};
' VB.NET version

Imports System
Imports Limilabs.Mail
Imports Limilabs.Client.POP3

Public Module Module1
    Public Sub Main(ByVal args As String())

        Using pop3 As New Pop3()
            pop3.ConnectSSL("pop.example.com")
            pop3.UseBestLogin("user", "password")

            Dim builder As New MailBuilder()
            For Each uid As String In pop3.GetAll()
                Dim eml = pop3.GetMessageByUID(uid)
                Dim email As IMail = builder.CreateFromEml(eml)

                Dim subject As String = email.Subject
            Next
            pop3.Close()
        End Using

    End Sub
End Module

POP3 explicit TLS/SSL mode

Mail.dll POP3 component connects using clear text channel and secures the channel using TLS/SSL by issuing STLS command. Typically standard POP3 port 110 is used, but this is not always the case. You can always specify different then standard port using Connect method overloads.

// C# version

using System;
using Limilabs.Mail;
using Limilabs.Client.POP3;

class Program
{
    static void Main(string[] args)
    {
        using (Pop3 pop3 = new Pop3())
        {
            pop3.Connect("pop.example.com");

            pop3.StartTLS();

            pop3.UseBestLogin("user", "password");

            MailBuilder builder = new MailBuilder();
            foreach (string uid in pop3.GetAll())
            {
                var eml = pop3.GetMessageByUID(uid);
                IMail email = builder.CreateFromEml(eml);

                string subject = email.Subject;
            }
            pop3.Close();
        }
    }
};
' VB.NET version

Imports System
Imports Limilabs.Mail
Imports Limilabs.Client.POP3

Public Module Module1
    Public Sub Main(ByVal args As String())

        Using pop3 As New Pop3()
            pop3.Connect("pop.example.com")

            pop3.STLS()

            pop3.UseBestLogin("user", "password")

            Dim builder As New MailBuilder()
            For Each uid As String In pop3.GetAll()
                Dim eml = pop3.GetMessageByUID(uid)
                Dim email As IMail = builder.CreateFromEml(eml)

                Dim subject As String = email.Subject
            Next
            pop3.Close()
        End Using

    End Sub
End Module

After you connect, you can check, if your POP3 server supports explicit TLS/SSL using following code:

// C# version

bool supportsSTLS = pop3.SupportedExtensions()
   .Contains(Pop3Extension.STLS);

' VB.NET version

Dim supportsSTLS As Boolean = pop3.SupportedExtensions() _
   .Contains(Pop3Extension.STLS)

You can read more here on how to know which extensions does your server support.

Self-signed certificates

If you are using self-signed certificates you may encounter this error: The remote certificate is invalid according to the validation procedure.


Get Mail.dll

Use TLS/SSL with IMAP in .NET

Mail.dll IMAP .NET email component supports Secure Socket Layer (SSL) and Transport Layer Security (TLS) protocols to authenticate the server and secure client-server email downloads.

There are two modes in which Mail.dll can work:

  • Implicit – where Mail.dll IMAP client immediately connects using secure channel,
  • Explicit – where Mail.dll IMAP client connects on unsecured channel first and then secures the communication by issuing STARTTLS command. This mode is sometimes called TLS.

In both cases, by default, Secure Sockets Layer (SSL) 3.0 and Transport Layer Security (TLS) 1.0, 1.1, 1.2, 1.3 are acceptable for secure communication. You can change the defaults using Imap.SSLConfiguration property.

Imap client may decide to secure the channel, if IMAP server explicitly forbids logging-in on unsecured channel and you are using UseBestLogin method.

Here you can find more details on SSL vs TLS vs STARTTLS, and here how to turn on TLS 1.2 in IMAP.

IMAP implicit TLS/SSL mode

Mail.dll IMAP component connects using secure TLS/SSL channel. You need to know in advance, if the server supports TLS/SSL connections – ask your administrator. Typically, IMAP over TLS/SSL is associated with port 993, but this is not always the case. You can always specify different then standard port by using ConnectSSL method overloads.

// C# version

using System;
using System.Collections.Generic;
using Limilabs.Client.IMAP;
using Limilabs.Mail;

class Program
{
    static void Main(string[] args)
    {
        using (Imap imap = new Imap())
        {
            imap.ConnectSSL("imap.example.com");
            imap.UseBestLogin("user", "password");

            imap.SelectInbox();

            List<long> uids = imap.Search(Flag.Unseen);

            foreach (long uid in uids)
            {
                var eml = imap.GetMessageByUID(uid);
                IMail email = new MailBuilder()
                    .CreateFromEml(eml);

                string subject = email.Subject;
            }
            imap.Close();
        }
    }
}
' VB.NET version

Imports System
Imports System.Collections.Generic
Imports Limilabs.Client.IMAP
Imports Limilabs.Mail

Public Module Module1
    Public Sub Main(ByVal args As String())

        Using imap As New Imap()
            imap.ConnectSSL("imap.example.com")
            imap.UseBestLogin("user", "password")

            imap.SelectInbox()

            Dim uids As List(Of Long) = imap.Search(Flag.Unseen)

            For Each uid As Long In uids
                Dim eml = imap.GetMessageByUID(uid)
                Dim email As IMail = New MailBuilder() _
                        .CreateFromEml(eml)

                Dim subject As String = email.Subject
            Next
            imap.Close()
        End Using

    End Sub
End Module

IMAP explicit TLS/SSL mode

Mail.dll IMAP component connects using clear text channel and secures the channel using TLS/SSL by issuing STARTTLS command. Typically standard IMAP port 143 is used, but this is not always the case. You can always specify different then standard port using Connect method overloads.

// C# version

using System;
using System.Collections.Generic;
using Limilabs.Mail;
using Limilabs.Client.IMAP;

class Program
{
    static void Main(string[] args)
    {
        using (Imap imap = new Imap())
        {
            imap.Connect("imap.example.com");
            imap.StartTLS();

            imap.UseBestLogin("user", "password");

            imap.SelectInbox();

            List<long> uids = imap.Search(Flag.Unseen);

            foreach (long uid in uids)
            {
                var eml = imap.GetMessageByUID(uid);
                IMail email = new MailBuilder()
                    .CreateFromEml(eml);

                string subject = email.Subject;
            }
            imap.Close();
        }
    }
}
' VB.NET version

Imports System
Imports System.Collections.Generic
Imports Limilabs.Mail
Imports Limilabs.Client.IMAP

Public Module Module1
    Public Sub Main(ByVal args As String())

        Using imap As New Imap()
            imap.Connect("imap.example.com")
            imap.StartTLS()

            imap.UseBestLogin("user", "password")

            imap.SelectInbox()

            Dim uids As List(Of Long) = imap.Search(Flag.Unseen)

            For Each uid As Long In uids
                Dim eml = imap.GetMessageByUID(uid)
                Dim email As IMail = New MailBuilder() _
                        .CreateFromEml(eml)

                Dim subject As String = email.Subject
            Next
            imap.Close()
        End Using

    End Sub
End Module

After you connect, you can check, if your IMAP server supports explicit TLS/SSL using following code:

// C# version

bool supportsStartTLS = imap.SupportedExtensions()
   .Contains(ImapExtension.StartTLS);
' VB.NET version

Dim supportsStartTLS As Boolean = imap.SupportedExtensions() _
   .Contains(ImapExtension.StartTLS)

You can read more here on how to know which extensions does your server support.

Self-signed certificates

If you are using self-signed certificates you may encounter this error: The remote certificate is invalid according to the validation procedure.


Get Mail.dll

Display HTML email in windows application

We have a special Windows control to do this – MailBrowserControl.

First you need to add reference to the three assemblies:

  • Mail.dll
  • MailBrowserControl.dll
  • ProtocolEx.dll

Add MailBrowserControl to the Toolbox:

Drag and drop the control on to the form.

Then just use Navigate method:

// C# version

private void button1_Click(object sender, EventArgs e)
{
    IMail mail = new MailBuilder().CreateFromEmlFile(@"HTMLMail.eml");
    mailBrowser1.Navigate(new MailHtmlDataProvider(mail));
}
' VB.NET version

Private Sub button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
	Dim mail As IMail = New MailBuilder().CreateFromEmlFile("HTMLMail.eml")
	mailBrowser1.Navigate(New MailHtmlDataProvider(mail))
End Sub

That’s it!

Note that all images and HTML are loaded from memory, no temporary files are created.

You can find a working example in the Mail.dll download package.

Send signed email using S/MIME

In this article we’ll show how to digitally sign email message and send it using Mail.dll email component. You’ll need to use S/MIME (sometimes called SMIME) standard to sign email.

S/MIME (Secure/Multipurpose Internet Mail Extensions) is a standard for public key encryption and signing of any MIME data including email messages.

S/MIME was originally developed by RSA Data Security. Specification uses Cryptographic Message Syntax (CMS), an IETF specification that is identical in most respects with PKCS #7.

S/MIME provides the following cryptographic security services for electronic messaging applications: authentication, message integrity, non-repudiation of origin (using digital signatures), privacy and data security (using encryption).

S/MIME signatures are usually done with what’s called “detached signatures”. The signature information is separate from the text being signed. The MIME type for such signed data is multipart/signed with the second part having a MIME subtype of application/(x-)pkcs7-signature. Mail.dll uses application/x-pkcs7-signature MIME entity to store S/MIME detached signatures.

Signing using MailBuilder

// C# version

MailBuilder b = new MailBuilder();
b.From.Add(new MailBox("mail@in_the_certificate.com", "Alice"));
b.To.Add(new MailBox("bob@mail.com", "Bob"));
b.Subject = "Test";
b.Html =                            // Set HTML body
    "This is <strong>signed</strong> message, " +
    "with embedded image:<br />" +
    "<img src = 'cid:image1' />.";

// Read attachment from disk...and add it to Visuals collection
MimeData image = b.AddVisual(@"c:\image.jpg");
image.ContentId = "image1";

b.SignWith(new X509Certificate2("TestCertificate.pfx", ""));

IMail email = b.Create();
' VB.NET

Dim b As New MailBuilder()
b.From.Add(New MailBox("mail@in_the_certificate.com", "Alice"))
b.[To].Add(New MailBox("bob@mail.com", "Bob"))
b.Subject = "Test"

' Set HTML body
b.Html = "This is <strong>signed</strong> message, " _
   + "with embedded image:<br />" _
   + "<img src = 'cid:image1' />."

' Read attachment from disk...and add it to Visuals collection
Dim image As MimeData = b.AddVisual("c:\image.jpg")
image.ContentId = "image1"

b.SignWith(New X509Certificate2("TestCertificate.pfx", ""))

Dim email As IMail = b.Create()

Signing using fluent interface

// C# version

IMail email = Mail
    .Html(@"<html><body>This is <strong>signed</strong> message with image <img src = 'cid:image1' /></body></html>")
    .Subject("Test")
    .From(new MailBox("mail@in_the_certificate.com", "Alice"))
    .To(new MailBox("bob@mail.com", "Bob"))
    .AddVisual(@"c:\image.jpg")
    .SetContentId("image1")
    .SignWith(new X509Certificate2("TestCertificate.pfx", ""))
    .Create();
' VB.NET

Dim email As IMail = Mail _
    .Html("<html><body>This is <strong>signed</strong> message with image <img src = 'cid:image1' /></body></html>") _
    .Subject("Test") _
    .From(New MailBox("mail@in_the_certificate.com", "Alice")) _
    .[To](New MailBox("bob@mail.com", "Bob")) _
    .AddVisual(@"c:\image.jpg") _
    .SetContentId("image1") _
    .SignWith(New X509Certificate2("TestCertificate.pfx", "")) _
    .Create()

Create test certificate

You can use following commands in VisualStudio Command Prompt to create test certificate:

makecert.exe -pe -r -sv Test_Keys.pvk -n "CN=John Doe,E=email@in-the-certificate.com" -sky exchange Test.cer

pvk2pfx.exe -pvk Test_Keys.pvk -spc Test.cer -pfx Test.pfx

If you use CER or PEM files you can find more information in this article:
Importing private/public keys or certificates in PEM, CER formats.

Sending signed email using SMTP

Now we can connect to SMTP server and send the email we recently created:

// C#

using (Smtp client = new Smtp())
{
    client.Connect("smtp.example.com"); // or ConnectSSL
    client.UseBestLogin("user", "password");
    client.SendMessage(email);
    client.Close();
}
' VB.NET

Using client As New Smtp()
	client.Connect("smtp.example.com") ' or ConnectSSL
	client.UseBestLogin("user", "password")
	client.SendMessage(email)
	client.Close()
End Using

By default Mail.dll uses SHA-1 alghoritm for signing. You can change this setting and choose different signature and encryption algorithm while sending S/MIME encrypted email message.

Validate S/MIME emails

In this article we’ll show how to verify digitally signed emails (S/MIME) using Mail.dll email component.

S/MIME (Secure/Multipurpose Internet Mail Extensions) is a standard for public key encryption and signing of MIME data.

S/MIME was originally developed by RSA Data Security. Specification uses Cryptographic Message Syntax, an IETF specification that is identical in most respects with PKCS #7. S/MIME provides the following cryptographic security services for electronic messaging applications: authentication, message integrity, non-repudiation of origin (using digital signatures), privacy and data security (using encryption).

S/MIME signatures are usually done with what’s called “detached signatures”. The signature information is separate from the text being signed. The MIME type for this is multipart/signed with the second part having a MIME subtype of application/(x-)pkcs7-signature.

Sometimes attached signatures (application/pkcs7-mime; smime-type=”signed-data”) format is used. In such case signature and data are represented by single MIME entity. Mail.dll recognizes both detached and attached signatures.

To check if the message has been signed use IsSigned property on IMail object.
CheckSignature(bool verifySignatureOnly) method is used for signature validation.

Using IMAP protocol

// C# 

using (Imap imap = new Imap())
{
    imap.Connect("imap.example.com"); // or ConnectSSL
    imap.UseBestLogin("user", "password");

    MailBuilder builder = new MailBuilder();
    foreach (long uid in imap.GetAll())
    {
        IMail email = builder.CreateFromEml(
            imap.GetMessageByUID(uid));

        // Check signature
        if (email.IsSigned == true)
            email.CheckSignature(true);
    }
    imap.Close();
}

' VB.NET

Using imap As New IMAP()
    imap.Connect("imap.example.com") ' or ConnectSSL
    imap.UseBestLogin("user", "password")

    Dim builder As New MailBuilder()
    For Each uid As Long In imap.GetAll()
        Dim email As IMail = builder.CreateFromEml( _
            imap.GetMessageByUID(uid))

        ' Check signature
        If email.IsSigned = True Then
            email.CheckSignature(True)
        End If
    Next
    imap.Close()
End Using

Using POP3 protocol

using (Pop3 pop3 = new Pop3())
{
    pop3.Connect("pop3.example.com"); // or ConnectSSL
    pop3.Login("user", "password");

    MailBuilder builder = new MailBuilder();
    foreach (string uid in pop3.GetAll())
    {
        IMail email = builder.CreateFromEml(
            pop3.GetMessageByUID(uid));

        // Check signature
        if (email.IsSigned == true)
            email.CheckSignature(true);
    }
    pop3.Close();
}
Using pop3 As New Pop3()
    pop3.Connect("pop3.example.com") ' or ConnectSSL
    pop3.Login("user", "password")

    Dim builder As New MailBuilder()
    For Each uid As String In pop3.GetAll()
        Dim email As IMail = builder.CreateFromEml( _
            pop3.GetMessageByUID(uid))

        ' Check signature
        If email.IsSigned = True Then
            email.CheckSignature(True)
        End If
    Next
    pop3.Close()
End Using

CheckSignature method will throw an exception, if it fails to verify the signature.