Another option is to use the "--admin" interface's "flush" command. This does forwarding in the context of the admin connection, so it could be used to increase the number of forwarding clients dynamically. One disadvantage is that if the admin connection goes away before forwarding is complete then you will likely end up with a failed (".bad") message. That means you might have to consider TCP idle timeouts and keepalives if the admin connection is quiescent for a long time while the flush command...
Thanks Graham That is very helpful Kind Regards Paul Paul Passingham Senior Deployment Specialist 020 7089 1410 Grosvenor Systems Limited We want to hear from you! Please take our NPS survey. https://t.xink.io/Tracking/Index/CXACAHIOAgAo5xsB0 Click here to explore our Professional Services Brochurehttps://t.xink.io/Tracking/Index/_D4CAHIOAgAo5xsB0 Grosvenor Systems Limited | Registration No. 1496717 (England) | Registered Office: 7 Leathermarket Street, London, SE1 3FB Any views or opinions expressed...
Or it might be easier to use the multi-config approach, as illustrated under 'advanced usage' in the userguide -- just add new forwarding sections to the existing config file: log log-format unit spool-dir ... port 25 forward-to ... ... fwd1-spool-dir ... fwd1-poll 10 fwd1-forward-to ... fwd1-no-smtp fwd2-spool-dir ... ...etc The disadvantage compared to having multiple processes is that it's more likely to get CPU-bound.
I found the problem these lines needed changing, though it didn't say anything about it. 60 $emailrelayClientOauth = "client oauth:b $Username" 61 $emailrelayAuthConfig = "$emailrelayClientOauth $saslXOAuth2" Thanks
Yes, the "client oauth:b ..." line should include the authentication name and the base64-encoded token, similar to the example in my userguide text. Can you get help from the script authors? It's difficult for me to help because while I did some testing many months ago I no longer have a 365 account and I do not speak powershell.
You can run as many emailrelay processes as you want, sharing the same spool directory. When one process is ready to send an email it renames an envelope file with a ".busy" filename extension in order to lock it and prevent any other process from picking it up. It might be best to use "--as-client" or "--dont-serve" or "--no-smtp" so that the processes do not all try to listen on the same server port (25 by default).
Multiple Client Connections
I run the first script ./create-m365-app-principals.ps1 with no issues, creates the application. I run the second script and it creates a emailrelay.auth file but the contents are client oauth:b test TEST_BASE64_ENCODED_XOAUTH2_TOKEN shouldn't the -UserPrincipialName I used be in there and a token? I did change below since I don't have emairlrelay actually running here but on my ubuntu server. $AuthFile = 'C:\ProgramData\E-MailRelay\emailrelay.auth' to $AuthFile = '/Users/markk/emailrelay.auth'
Please take a look at https://sourceforge.net/p/emailrelay/support-requests/121/ Following on from the ugg.li guys' work I wrote this to go into the emailrelay user guide in the next release: Microsoft 365 ------------- E-MailRelay can forward e-mails to a Microsoft 365 Exchange server for onward delivery. Set the "--forward-to" address to "smtp.office365.com:587", and enable authentication and TLS by using the "--client-auth" and "--client-tls" options, or add these lines to the "emailrelay.cfg"...
having trouble setting up
I Patched and test it. It seems fine and works as expected when respond "100" over network filter
Patch it and test it. It seems fine and works as expected when respond "100" over network filter
The short answer is just add a "forward" line to the emailrelay configuration file, which is "C:\ProgramData\emailrelay\emailrelay.cfg" by default. # emailrelay.cfg log verbose forward-to smtp.example.com:25 forward poll 60 ... (If using an old version of emailrelay you would instead add "--forward" to the command-line in the "emailrelay-start.bat" batch file.) Note that the emailrelay-service.exe service wrapper interfaces to the windows service subsystem, but in the end it runs "emailrelay.exe"...
Ok, but "how"? ;-) While the windows service just starts the emailrelay-service.exe directly - or do I need to manipulate the start string in the registry itself while adding the --forward?
I think all you need is to add "--forward". It triggers forwarding when the server starts up, so there is no need to wait for the first poll period.
Instant spool processing on startup
The only changes that could affect a filter when upgrading to a new version of emailrelay are (1) the command-line now has two arguments (content and envelope) and (2) the fields in the envelope file will be different. The transfer encoding is part of the content file and emailrelay does not know anything about message content (except that it adds a Received header) -- it treats the message content as an opaque string of bytes. You should run your filter test first with just the content file on the...
So are using this scenario: For a long-lived relay the server side is enabled by default, and on the client side you must choose when to forward with some combination of "poll", "forward-on-disconnect", "admin", and also define the "forward-to" address. Relay is working. Filter is failing. It looks like it fails due to email content-transfer-encoding. It works when sending email in plain text.
Thank you for the very fast fix. I can confirm, that it works now as expected.
Configuring emailrelay as a server is a no-op since by default it listens on port 25 and spools to the standard spool directory. To configure as a long-lived client you need to disable port 25 with "no-smtp", define the "forward-to" address and provide some way to trigger forwarding, typically with "admin" or "poll". For a short-lived, one-shot client you need to disable all network serving with "dont-serve" and enable forwarding at startup with "forward" and also define the "forward-to" address...
I have added the fix to the V_2_6_fixes branch in the sourceforce subversion repository, with a self-reporting version of "2.6b". It is also in HEAD in the two github repositories (graeme-walker/emailrelay and graeme-walker/emailrelay-build). The emailrelay-build repository update has triggered a windows build with the built binaries available under actions->v2.6b->artifacts->executables.
v2.5 fix for client-filter exit 102 and mx lookup over ipv6
v2.6 fix for client-filter exit 102
I looks like that functionality was accidentally dropped in v2.5. Apologies. The fix in src/gsmtp/gsmtpforward.cpp is to check the filter's special-handling flag before sending the next message, which is on line 291 for v2.5 and line 295 for v2.6: if( special || !sendNext() ) // v2.5 line 291 if( info.filter_special || !sendNext() ) // v2.6 line 295
Lastly, if the emails contain anything other than plain text or HTML, do I need to use MimeKit/BouncyCastle? Emails coming from SP will contain all kinds of stuff.
I think I am ok based on your first response. I forgot to add --forward-on-disconnect to my final e-mailrelay configuration (I don't think the filter program returns the right code on exit). So no forwarding was happening. We have ServerA setup as a relay forwarding to ServerB to send mail. So I was wondering if I should think of ServerA (and configure) as a server and a client like I did for my manual test? I don't think I need to when using --forward-to and --forward-on-disconnect. I read somewhere...
Mails are getting sent directly instead of one per minute when using --client-filter exit:102 and --poll 60
I don't understand your distinction between virtual and actual, but email is a store-and-forward messaging system so an email message can go through any number of "transfer agents" where each transfer agent acts as a server to accept incoming messages and also acts as a client to forward them on. E-MailRelay is normally used as a simple store-and-forward relay that does not do any routing itself, so it typically forwards to a dedicated "smarthost" that does routing directly to the recipients' se...
Question. Is my configured relay server acting as a server and client if I have to forward mail to another virtual server acting on behalf of my actual mail server? On Wed, Sep 17, 2025 at 5:44 PM Graeme Walker graeme_walker@users.sourceforge.net wrote: I suppose to make the same point more generally, you should be able to do some regression testing of your filter against different versions of emailrelay without actually running an emailrelay server; just use emailrelay-submit (for example) to create...
Got it! On Wed, Sep 17, 2025 at 5:44 PM Graeme Walker graeme_walker@users.sourceforge.net wrote: I suppose to make the same point more generally, you should be able to do some regression testing of your filter against different versions of emailrelay without actually running an emailrelay server; just use emailrelay-submit (for example) to create files in the spool directory and pass the filenames on the filter command-line. Envelope and content files created by old versions of emailrelay and emailrelay-submit...
I suppose to make the same point more generally, you should be able to do some regression testing of your filter against different versions of emailrelay without actually running an emailrelay server; just use emailrelay-submit (for example) to create files in the spool directory and pass the filenames on the filter command-line. Envelope and content files created by old versions of emailrelay and emailrelay-submit should be usable by newer versions.
I'm glad you're making progress. To see what your compiled filter "script" is doing I would just run it from visual studio, without any involvement from emailrelay -- just configure debuggee command-line in visual studio to have the full path of the envelope and content files, but note that prior to version 2.1 emailrelay put only the content file on the filter command-line.
I think I have figured out the manual command line execution steps: Step 1 - configure relay to store e-mail to spool dir (must use relay server FQDN to see content as it is relayed) Step 2 - send email via PS (From PS send to relay server FQDN) Step 3 - examine email content and envelope and manually change content or email envelope as a test Step 4 - use relay as client and forward updates mail to host that actually delivers email (From CMD issue--> emailrelay --as-client [host:port] --spool-dir...
Thank you for responding so quickly. The forwarding configuration is in my configuration file. I now see that running the service and the command line result in two different instances of the relay. I stopped the service and would like to issue the process via commands via the CMD window. This is the old configuration via the start batch file: start "emailrelay" w:\work\E-MailRelay\emailrelay.exe -e -p 25 -o [mail host]:25 -l -i w:\work\E-MailRelay\emailrelay.pid -O 0 -r -s w:\work\E-MailRelay\spool...
By default there is no forwarding (you do not have "--as-client" or "--forward-to" on your command line) so it just spools up whatever is submitted by the remote client. Forwarding can be done by running "emailrelay --as-client ...." separately, or add "--forward-to ..." to the server command line with "--poll" or "--forward-on-disconnect". You should check that nothing else is listening on port 25 ("netstat -an -p tcp") that might be confusing things. If anything connects to your emailrelay server...
Testing E-MailRelay
I don't need it right now. I'm just curious because I haven't seen any update in a long time on this issue :) Thanks.
Hi Yunus. I have this ready for the 2.7 release, but if you need it now I have attached a patch against the 2.6 source. (Apply with "patch -p1 < patch-fr40.p1".)
Hello Graeme, hope you're doing well. Is there anything I can do to help with this development?
No, I'm not a fan of that game. I've played it before. Some virus scanners, particularly those with "AI" in the name, seem to be just random number generators with a commercially-sponsored whitelist attached. Even if a trivial rebuild passes today then there is no guarantee for tomorrow. FYI, for the 2.6 release I used an "air-gapped" Microsoft WinDev VM for the build. The code and all its dependencies are on GitHub https://github.com/graeme-walker/emailrelay-build , in case anyone wants to do their...
OK, not sure if you can try and re-compile after changing the code a bit to see if it will help with ESET block.
It creates a self-signed X509 certificate so that you can run an SMTP server with TLS, It is run by the emailrelay-setup installer if you check the "enable TLS encryption" checkbox on the "SMTP server" page without specifying a certificate file. If emailrelay-keygen.exe does not exist then you are forced to supply your own certificate file before the "next" button is enabled. See also: https://sourceforge.net/p/emailrelay/support-requests/114/
emailrelay-keygen.exe flagged as suspicious by AV and VirusTotal
Thanks for your help, I succeeded setting it up :)
I think you just need to remove the "--filter=mx:". You have the mx filter running server-side with the default 127.0.0.1 name server address, so it fails the message. The client-side filter with the correct nameserver address never runs at all. Also note that the split filter should be the last server-side filter because it might create new messages and any subsequent server-side filters will only operate on the original message and not the copies.
I'm working on Windows servers, the DNS is also Windows. I'm running this command, but the DNS still pointing to localhost: emailrelay.exe --as-server --filter=split: --client-filter="mx:10.1.1.1:53" --forward-to=127.0.0.1:9 --spool-dir=C:\ProgramData\E-MailRelay\Spool --filter=mx: --verbose --verbose --log-file=C:\ProgramData\E-MailRelay\ManualLogs\emailrelay-log-%d.txt emailrelay: info: filter [split:,mx:]: [emailrelay.266396.1754637303.1] emailrelay: info: filter [split:] updating emailrelay:...
I suppose your default nameserver addresses might be unix-domain sockets. Try specifying the nameserver address explicitly. Also use --verbose twice to get more logging from the mx filter.
Send via MX
https://sourceforge.net/projects/emailrelay/files/emailrelay/2.6/emailrelay_2.6_arm64_rpi_deb12.deb/download
No, not easily. Can you try to build it natively on the rpi? You need to install things like g++, automake, debhelper, libssl-dev and then build emailrelay with ./configure.sh, make, make deb. FWIW I have done a cross-compilation using debian 12 on linux with libressl-4.1.0, but I cannot test it in any way. The main emailrelay binary is here: https://sourceforge.net/projects/emailrelay/files/OldFiles/emailrelay-2.6-arm-linux-gnueabihf-libressl/download
Create arm emailrelay_x.x_arm64-deb12.deb
True, a non-virtual account would allow further restrictions. Still, the virtual service account is already much more secure than LocalSystem, so I'm happy with the solution. It hits the sweet spot balancing security and convenience for me.
Unfortunately the virtual service account is a member of the Users group, which allows it to create files with few restrictions. That makes it pretty useless for a zero-trust install, as far as I can see (IANAWA). For that I think you would have to set up a (non-virtual) account with a password and take a hit on password management.
Thank you very much for your explanation. Now I understand. I was not wrong before. It should be that something else interrupted the connection.
The log file shows that the remote client disconnected unexpectedly when sending the NDR message content. The message was not rejected by emailrelay; the sender failed to send it.
On reflection, modifying one of the built-in filters will given you a good idea of any overhead from running a script, but to avoid reading and writing the envelope file a more direct approach would be to fill in the client-account-selector at the time the envelope is first created. That is in GStore::NewFile::prepare() in src/gstore/gnewfile.cpp; add a line m_env.client_account_selector = peer_socket_address where it says 'save the envelope'. On Windows I would be interested to know whether you...
The version I use is 2.5.2 But I was rejected, I hope he can accept it
Thanks for the quick response and I appreciate my primary question was rather nebulous. The one server/multiple forwarding agents setup sounds achievable. I suppose I could benchmark this performance by simply operating our current setup as a server without forwarding. I could then time the inbound spooling. I'll certainly give that code change a try, thanks for highlighting where I'd need to look. Unfortunately we're running all this on a Windows 2022 Server. Have you any non-specific, top-level...
I can't really comment on the throughput you are seeing because there are so many variables. One thing to bear in mind is that emailrelay runs as a single process and (mostly) using a single thread. It works asynchronously, so multiple connections are handled concurrently, but even so, for high performance you should try running multiple emailrelay processes sharing the same spool directory -- typically one server and multiple forwarding agents. If you can have multiple servers so much the better,...
Yes, an empty MAIL-FROM address will be accepted with just a warning in versions up 2.5.2, although version 2.6 has a bug where empty MAIL-FROM addresses will be rejected. If you want to reject NDRs you should use an address verifier that checks whether the second command-line parameter is empty or use a filter that examines the envelope file's "From" field.
Throughput and ClientAccountSelector
about NDR
I should add that the keygen executable is optional, so you can delete it from the release zipfile. The only consequence will be that if you enable server-side TLS in the installation GUI it will require an existing certificate file rather than generating one itself.
False positive in 'emailrelay-keygen.exe'
Thanks for taking the trouble to let me know. There are only a few dozen lines of code in that executable that are not from the MbedTLS project (until recently part of Arm Holdings), so quite easy to audit. The released binaries were built on a VM from Microsoft, with no network access. If you want to do your own clean-room build you should look at the "emailrelay-build" repository on github. My own experiments with virus-scanning aggregators have led me to the conclusion that their false positive...
False positive in 'emailrelay-keygen.exe'
Just ended up using enabling feature today, after discovering a legacy app that unfortunately cant be adjusted.
Glad to hear that it's useful. Oh, and thanks for your help and for maintaining E-MailRelay! Since Microsoft removed its built-in SMTP server in Windows Server 2025 and hMailServer is no longer maintained, there are not many simple and free mail forwarding alternatives left on the Windows platform.
That's really useful, thank you. I'll add that information to the 'running as a service' section of the emailrelay 'windows' document.
It worked! I changed the service user to its virtual service account and granted modify permissions to emailrelay.pid, the spool directory and the log directory. Here are the exact cmd commands I used. (To future readers: note that I used a non-standard log directory, you might need to change that path.) net stop emailrelay sc config emailrelay obj= "NT Service\emailrelay" icacls "C:\ProgramData\E-MailRelay\emailrelay.pid" /grant "NT Service\emailrelay":M icacls "C:\ProgramData\E-MailRelay\spool"...
Thanks for the feedback. I agree that userid switching on Windows probably won't make sense: AFAIK, Windows does not have the "privileged ports < 1024" restriction that requires root on Unix, and you cannot easily do a "user switch without a password" anyway. The idiomatic way on Windows is to run the service itself with a lower-privileged account. As "output", I guess documentation, i.e. a checklist of permissions that are required, would already be a helpful first step for users who want to harden...
That's a good idea. I expect this has been done many times, but I have had no feedback to share with you. In my (limited) understanding you can set the account used by the service easily enough using the "Services" tool. The emailrelay service is actually a service wrapper that executes the emailrelay server in a separate process, and the account propagates from the service wrapper, on to the main emailrelay server process, and then on to any filter or address-verifier scripts. If you control the...
(Should be NT Service\Servicename, the backslash messed up the formatting.)
Reducing permissions as a Windows service
Many thanks Graeme PS Would it make sense to have a section on the website to list a list of common scripts, such as the one you developed?
I've attached a javascript (or rather MS JScript) filter script. I normally use perl for scripting and I've never taken to powershell, I'm afraid. The script examines the envelope-from address and all envelope-to addresses and then rejects the message if any domain is not in the hard-coded list. You will need to edit the list of allowed domains and possibly delete either the 'check envelope-from' section or the 'check envelope-to' section depending on your requirements.
Thanks Graeme, I basically forwarding messages onwards via a smarthost (M365) and I just need to reject any message if the domain part is not in the approved list. Unfortunately I have to use Windows, do you have any example scripts I can use ( PowerShell would be preferable) . Thanks in advance
Thanks for your kind comments. I'm not completely clear what you are after though. Do you need to check the envelope-from address (ie. MAIL FROM) and reject the message if the domain part is not in the approved list? Or perhaps do a mapping from the legacy app's envelope-from address to one that is allowed? If emailrelay is doing simple store-and-forward you can use a "--filter" script (or "--client-filter") to check any part of an email message, including submitter's IP address, EHLO domain, envelope-from...
verifying sender domains
From what you have said you should only need to edit the "From:" header in the message content using the "emailrelay-set-from.js" filter script (as discussed), but for completeness I have also attached a new script (based on "emailrelay-edit-envelope.js") to set the 'from' address in the envelope. Edit it to set the required address and run both scripts using two separate "--filter" command-line options or two separate "filter" lines in the configuration file.
Yes, that's even easier: use the example script "emailrelay-set-from.js" as the "--filter" script. Edit the "new_from" variable as required.
Thank you for the script. I went back and forth with the upstream email provider (SMTP2Go) and now they are changing their story. It's not the comma in the subject causing a problem, it's a comma in the FROM field that MailRelay is accepting and then passing to the next hop. SMTP2Go support sent me an example of a header that is problematic: Received: from 10.15.241.108 by smtpcorp.com with esmtpa (Exim 4.97.1-S2G) (envelope-from voicemail@domainname.org) id 1u6ys0-4o5NDgrv5fh-dDl3 for <redacted>...
So as per our DM, I would suggest using the example filter script "emailrelay_set_from.js" as a starting point for editing header fields such as "Subject:". I've attached a version that removes subject commas, but you might want to change the 'replacement' variable to be a space or an underscore or whatever. You will need to add a "--filter" option to the emailrelay command-line that refers to the filter script, typically as a "filter ...." line in the "emailrelay.cfg" configuration file. I don't...
Removing commas from outbound email message
v2.6 fix for empty envelope-from
Don't worry I discovered iLo wont send sharing the same subnet? This is the whole reason I got E-MailRelay. I am having this issue: https://community.hpe.com/t5/proliant-servers-ml-dl-sl/ilo-won-t-send-test-alert-emails-to-local-smtp-server/td-p/6752732
HP iLo 4
v2.6 fixes branch
[...] documentation, which has apparently been written by a committee of corporate lawyers. It is :-) However, the link is not working for me at the moment -- please could you check? Hm, works from this end (right now). Just a (public) github repository, no bells, no whistles. Any error messages? these tickets are my preferred way of supporting emailrelay ✅ We will stay here. Thanks for your positive answer (and the E-Mailrelay software, obviously). Maybe these scripts help other folks trying to...
You are right that others have asked for help in this area, so I would be very happy to send them your way. Congratulations on deciphering the Microsoft documentation, which has apparently been written by a committee of corporate lawyers. However, the link is not working for me at the moment -- please could you check? For direct messaging you can begin with my sourceforge email address, but these tickets are my preferred way of supporting emailrelay -- or the github repository can be used for collaborative...
Microsoft 365 (Exchange Online) "addon" for E-MailRelay
You can ignore the close errors. When running as a detached daemon process it is a good idea to close unused inherited file descriptors so as to not stop file systems from being unmounted. Unfortunately it is not possible to get a list of open file descriptors, so you have to close potentially hundreds of file descriptors that are already closed. You can take off the emailrelay --daemon option to stop it doing that. I am hoping that you will get an strace output that shows the verifier process being...
I think I mucked up the -f side with the -e... So without the -e: write(2, "emailrelay: info: rx<<: \"rcpt to"..., 45emailrelay: info: rx<<: "rcpt to: q@w.com" ) = 45 getpid() = 25 socket(AF_UNIX, SOCK_DGRAM|SOCK_CLOEXEC, 0) = 10 connect(10, {sa_family=AF_UNIX, sun_path="/dev/log"}, 110) = -1 ENOENT (No such file or directory) close(10) = 0 write(2, "emailrelay: info: address verifi"..., 152emailrelay: info: address verifier: executing [/config/app/emailrelay/verify.sh] [q@w.com] [qq@qq.com] [172.17.0.1:47828]...
selinux is disabled? getenforce Disabled
So the verifier execve() is not showing in the trace, even with strace's "-f" option. But I notice your "app" and "config" directories have an extra "." after the permissions, which apparently indicates some sort of SELinux secutity setting. Is SELinux hijacking the exec() system call before strace gets to see it? It's not something I know a lot about. Can you see if there is a SELinux log, or try disabling it temporarily?