Dropping connections by aiosmtpd when receiving email - aiosmtpd

I am using python3, aiosmtpd to capture emails from a dvr on a private lan and strip the attachments. I've written a handler for aiosmtp and some test python to send an email with attachment, plain, no encryption and it works. When the dvr sends email it yields connection lost.
I tried debugging using:
python3 -m aiosmtpd -d -n -l 192.168.66.1:11125
Adding "--no-requiretls" doesnt seem to change result.
List item
This is result:
2021-06-07 21:29:30 - Available AUTH mechanisms: LOGIN(builtin) PLAIN(builtin)
Available AUTH mechanisms: LOGIN(builtin) PLAIN(builtin)
2021-06-07 21:29:30 - Peer: ('192.168.66.99', 47054)
Peer: ('192.168.66.99', 47054)
2021-06-07 21:29:30 - ('192.168.66.99', 47054) handling connection
('192.168.66.99', 47054) handling connection
2021-06-07 21:29:30 - ('192.168.66.99', 47054) >> b'EHLO 192.168.66.1'
('192.168.66.99', 47054) >> b'EHLO 192.168.66.1'
2021-06-07 21:29:31 - ('192.168.66.99', 47054) >> b'AUTH LOGIN'
('192.168.66.99', 47054) >> b'AUTH LOGIN'
2021-06-07 21:29:31 - ('192.168.66.99', 47054) connection lost
('192.168.66.99', 47054) connection lost
2021-06-07 21:29:31 - ('192.168.66.99', 47054) Connection lost during _handle_client()
('192.168.66.99', 47054) Connection lost during _handle_client()
smtp.py, part of aiosmtpd 1.4.2 installed by pip3:
def __init__(
...
auth_require_tls=True,...)
...
self._auth_require_tls = auth_require_tls
async def smtp_AUTH(self, arg: str) -> None:
...
elif self._auth_require_tls and not self._tls_protocol:
return await self.push("538 5.7.11 Encryption required for requested authentication mechanism")
So the above default if AUTH received will fail because init, if not set by user code leaves _auth_require_tls as True. As the AUTH is plain in this case the protocol won't be tls.
A bit more debug and I found that the client is not responding to challenge.
INFO:mail.log:('192.168.66.99', 47054) << challenge: b'334 VXNlciBOYW1lAA=='
Not sure what to try now. Any suggestions?

Related

Socat - certificate rotation for mTLS connection - reload credential files interval

Use case:
I use socat to stream traffic between some app and external world via Squid (app->socat->Squid). To authenticate in SQUID I use mTLS.
My socat usage:
socat -d -d tcp-listen:3128,reuseaddr,fork \
openssl-connect:<SQUID_IP>:3128,cert=client-cert-key.pem,cafile-squid=squid-ca.crt,openssl-commonname=<SQUID_CN>-prd,keepalive
where
content of the PEM and CERT filles rotate.
Problem: If I put some trash into squid-ca.crt file socat after a couple of seconds catches the change and logs errors:
socat[72] E SSL_connect(): error:1416F086:SSL routines:tls_process_server_certificate:certificate verify failed
socat[72] N exit(1)
socat[9] N childdied(): handling signal 17
, and when I recover squid-ca.crt file socat ater some time (several to several dozen seconds) fetches the change and starts working again with with the recovered data.
Is there an option to control the time on files probing by socat?
Socat with your command waits for client connections and forks a new sub process for each one. Only in these sub processes the OpenSSL module is initialized and the certificate loaded.
So it is not some timing but just depends on the next TCP connection to arrive.

Could not set variable "USER.user_false_counter" as the collection does not exist in ModSecurity logs Apache (Windows OS)

We are using apache module for our web server(windows OS). We need to prevent unsuccessful authentication attempt by the user. Hence we thought to use Mod Security module. I uses this standard configuration setting in "modsecurity-minimal.conf" as below
SecStatusEngine On
SecRule IP:bf_block "#eq 1"
"id:'2000004',phase:4,deny,
logdata:'Access denied [by IP] IP: #%{REMOTE_ADDR}, user: %{USER.name}'
SecRule USER:bf_block "#eq 1"
"id:'2000005',phase:4,deny,
logdata:'Access denied [by USER] IP: #%{REMOTE_ADDR}, user: %{USER.name}'
SecRule REQUEST_HEADERS:authorization "Basic ([a-zA-Z0-9]+=*)$" "phase:3,nolog,pass,id:2000012,chain,capture"
SecRule TX:1 "^([-a-zA-Z0-9_]+):" "t:base64Decode,chain,capture"
SecAction initcol:USER=%{TX.1},setvar:USER.name=%{TX.1},initcol:IP=%{REMOTE_ADDR}
SecRule RESPONSE_STATUS "401" \
"phase:5,pass,id:2000015,chain,logdata:'basic auth de #%{IP}, var: %{IP.begin}, user: %{USER.name}, ufc: %{USER.user_false_counter}, block: %{USER.bf_block}, IPblock: %{IP.bf_block}, ifc: %{IP.ip_false_counter}'"
SecAction setvar:USER.user_false_counter=+1,setvar:IP.ip_false_counter=+1,expirevar:USER.user_false_counter=300,expirevar:IP.ip_false_counter=300
# Check for too many failures for a single username, blocking 30 seconds after 3 tries
SecRule USER:user_false_counter "#ge 2" \
"id:'2000020',phase:3,t:none,pass,\
setvar:USER.bf_block,\
setvar:!USER.user_false_counter,\
expirevar:USER.bf_block=30"
# Check for too many failures from a single IP address. Block for 5 minutes after 10 tries.
SecRule IP:ip_false_counter "#ge 2" \
"id:'2000021',phase:3,pass,t:none, \
setvar:IP.bf_block,\
setvar:!IP.ip_false_counter,\
expirevar:IP.bf_block=300"
However when I see the modsec_debug.log, I get following error.
Could not set variable "USER.user_false_counter" as the collection does not exist.
Could not set variable "IP.ip_false_counter" as the collection does not exist.
Please help me how to resolve this issue.
This is a very complicated rule set (Is it taken from the ModSec Handbook?) and it may take hours to debug it. So it is not likely you will get the right support here.
What I can see immediately, is that you are not always initializing the collection and there is a chance rule 2000015 hits without the initialization. That is when a browser requests a resource without basic auth, the server responds with 401, then your rule 2000015 hits and only on the subsequent request would the browser request the same URI with the basic auth header.
So it looks to me as if your logic / rule architecture was garbled.
When I write complicated rule sets like this, I log every rule and I write and test them step by step and only if every rule works on its own, then I start to put them together, then I optimize them and then I put most of them to nolog.
This may take some time, so be warned.

Asyncio RuntimeError: readuntil() called while another coroutine is already waiting for incoming data

Using python3.6.8:
I'm attempting to script the initial configuration of network devices on boot. My script opens telnet connection on "ip_addr:port". Once connected, script stimulates the network device it's connecting to with "\n\n" (simulating two 'Enter' input from an admin).
connection = asyncio.open_connection(
ip_addr,
port,
)
try:
reader, writer = await asyncio.wait_for(connection, 5)
print(f"successfully connected to {ip_addr}:{port}")
writer.write(b'\n\n\n')
Some devices are already configured and I except " login: " to show up in the read buffer upon entering '\n'. However if the device is not configured yet, " login: " will not show up in the buffer. Therefore I thought I could use wait_for and timeout option to have this cancelled and move on with another reader.readuntil(...) expecting another output.
try:
await asyncio.wait_for(reader.readuntil(b' login: '), 3)
print(f"{ip_addr}:{port} alredy booted")
break
except (asyncio.TimeoutError, OSError):
print('Nope, moving forward')
await reader.readuntil(b'normal setup ?(yes/no)[n]: ')
However this raises a RuntimeError. Reading the documentation I excepted the task to be cancelled if the timeout is reached, so why can't it have another coroutine readuntil() ?

.Net FTPS Connection times out after sending 'CCC' command

I've been struggling a lot these last few days with a FTPS server that requires the 'CCC' command I'm trying to access via .Net
I'm using AlexFTPS Library. I'm able to connect and negociate AUTH TLS, I'm able to change directory but when I'm trying to list directory or download files, server asks for 'CCC' command. When I send 'CCC' command, I get a '200 CCC Context Enabled' reply but then I cannot send anything else, anytime I get a server timeout exception.
I've done further tests :
WS_FTP : works if I check the 'Use unencrypted command channel after SSL authentication' option
Filezilla : does not work even if I add 'CCC' as a Post Login Command
http://www.componentpro.com/ftp.net/ : works but is not open source
Any help would be so much appreciated... Sorry I am not FTP fluent...
Here's my code :
Using Client As New AlexPilotti.FTPS.Client.FTPSClient
AddHandler Client.LogCommand, Sub(sender As Object, args As AlexPilotti.FTPS.Common.LogCommandEventArgs)
Console.WriteLine(args.CommandText)
End Sub
AddHandler Client.LogServerReply, Sub(sender As Object, args As AlexPilotti.FTPS.Common.LogServerReplyEventArgs)
Console.WriteLine(args.ServerReply)
End Sub
Dim cred = New Net.NetworkCredential("login", "password")
Client.Connect("ftps.server.com", cred, AlexPilotti.FTPS.Client.ESSLSupportMode.CredentialsRequired)
Client.SendCustomCommand("SYST")
Client.SendCustomCommand("PBSZ 0")
Client.SendCustomCommand("PROT P")
Client.SendCustomCommand("FEAT")
Client.SendCustomCommand("PWD")
Client.SendCustomCommand("TYPE A")
Client.SendCustomCommand("PASV")
Client.SendCustomCommand("CCC")
Client.SendCustomCommand("LIST")
Console.ReadKey()
End Using
Thanks !
CCC ("Clear Command Channel") is a special command which downgrades the connection from SSL (started with AUTH TLS) back to unencrypted again. So it's no enough to just declare it as a custom command which gets send on the established control connection, it has to be handled similar to AUTH TLS by the FTPS library so that after the command is done the TLS downgrade occurs.

IMAP connection carriage return line feed issue from linux?

I'm attempting to connect to our exchange server using Mail::IMAPClient but a script that was working is having issues when I moved it from a temp dev desktop running ubuntu to a new dev env running centos. During that time I found out the exchange server was upgraded I think to 2010. Is there a setting in exchange that would allow commands to be processed with just linefeeds instead of requiring crlf or could this be a local system (running the script issue)?
This just times out after a while.
$openssl s_client -connect myhost.mydomain.net:993
...
* OK The Microsoft Exchange IMAP4 service is ready - 'myhost'
? login username password
* BYE Connection is closed. 13
read:errno=0
Commands would function correctly.
$openssl s_client -crlf -connect myhost.mydomain.net:993
...
* OK The Microsoft Exchange IMAP4 service is ready - 'myhost'
? login username password
? OK LOGIN completed.
? select inbox
* 4 EXISTS
* 0 RECENT
* FLAGS (\Seen \Answered \Flagged \Deleted \Draft $MDNSent)
* OK [PERMANENTFLAGS (\Seen \Answered \Flagged \Deleted \Draft $MDNSent)] Permanent flags
* OK [UNSEEN 3] Is the first unseen message
* OK [UIDVALIDITY 169533] UIDVALIDITY value
* OK [UIDNEXT 132] The next unique identifier value
? OK [READ-WRITE] SELECT completed.
1 logout
* BYE Microsoft Exchange Server 2010 IMAP4 server signing off.
1 OK LOGOUT completed.
read:errno=0
[Solution:]
Tried to make a manual ssl connection to the server using openssl.
I had to include the -crlf option so that exchange could recognize the IMAP commands terminating.
It's in section 2.2 of RFC3501, but that's part of the overview.
All interactions transmitted by client and server are in the form of lines, that is, strings that end with a CRLF.
Note that there is no "MUST" in the clause.
Dovecot and other IMAP servers are more liberal about what they accept, in terms of what constitutes an EOL.
"Correctness" is relative. If there's no MUST or SHOULD clause it's generally accepted that "be liberal in what you accept and strict in what you send" is the best way forward when implementing RFCs.
IMAP protocol requires the client and server to use \r\n.
Exchange behaves correctly (which is not that common).

Resources