SNode.C
Loading...
Searching...
No Matches
SocketWriter.cpp
Go to the documentation of this file.
1
/*
2
* SNode.C - a slim toolkit for network communication
3
* Copyright (C) Volker Christian <me@vchrist.at>
4
* 2020, 2021, 2022, 2023, 2024, 2025
5
*
6
* This program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU Lesser General Public License as published
8
* by the Free Software Foundation, either version 3 of the License, or
9
* (at your option) any later version.
10
*
11
* This program is distributed in the hope that it will be useful,
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
* GNU Lesser General Public License for more details.
15
*
16
* You should have received a copy of the GNU Lesser General Public License
17
* along with this program. If not, see <http://www.gnu.org/licenses/>.
18
*/
19
20
#
include
"core/socket/stream/tls/SocketWriter.h"
21
22
#
ifndef
DOXYGEN_SHOULD_SKIP_THIS
23
24
#
include
"core/socket/stream/tls/ssl_utils.h"
25
#
include
"log/Logger.h"
26
#
include
"utils/PreserveErrno.h"
27
28
#
include
<
cerrno
>
29
#
include
<
openssl
/
ssl
.
h
>
30
#
include
<
string
>
31
32
#
endif
// DOXYGEN_SHOULD_SKIP_THIS
33
34
namespace
core::socket::
stream
::
tls
{
35
36
ssize_t
SocketWriter
::
write
(
const
char
*
chunk
,
std
::
size_t
chunkLen
) {
37
ssize_t
ret
= 0;
38
39
if
((
SSL_get_shutdown
(
ssl
) & SSL_SENT_SHUTDOWN) != 0) {
40
ret
=
Super
::
write
(
chunk
,
chunkLen
);
41
}
else
{
42
ret
=
SSL_write
(
ssl
,
chunk
,
static_cast
<
int
>(
chunkLen
));
43
44
if
(
ret
<= 0) {
45
const
int
ssl_err
=
SSL_get_error
(
ssl
,
static_cast
<
int
>(
ret
));
46
47
switch
(
ssl_err
) {
48
case
SSL_ERROR_WANT_READ:
49
LOG(
TRACE
) <<
getName
() <<
" SSL/TLS: Start renegotiation on read"
;
50
doSSLHandshake
(
51
[
this
]() {
52
LOG(
DEBUG
) <<
getName
() <<
" SSL/TLS: Renegotiation on read success"
;
53
},
54
[
this
]() {
55
LOG(
WARNING
) <<
getName
() <<
" SSL/TLS: Renegotiation on read timed out"
;
56
},
57
[
this
](
int
ssl_err
) {
58
ssl_log
(
getName
() +
" SSL/TLS: Renegotiation"
,
ssl_err
);
59
});
60
errno = EAGAIN;
61
ret
= -1;
62
break
;
63
case
SSL_ERROR_WANT_WRITE:
64
errno = EAGAIN;
65
ret
= -1;
66
break
;
67
case
SSL_ERROR_ZERO_RETURN:
// shutdown cleanly
68
LOG(
DEBUG
) <<
getName
() <<
" SSL/TLS: Close_notify received. Is EOF? "
<< (
closeNotifyIsEOF
?
"true"
:
"false"
);
69
errno =
closeNotifyIsEOF
? EPIPE : EAGAIN;
70
ret
= -1;
// on the write side this means a TCP broken pipe
71
break
;
72
case
SSL_ERROR_SYSCALL:
73
// In case ret is -1 a real syscall error (RST = ECONNRESET)
74
{
75
const
utils
::
PreserveErrno
pe
;
76
77
if
(errno == EPIPE) {
78
PLOG(
WARNING
) <<
getName
() <<
" SSL/TLS: Syscal error (SIGPIPE detected) on write."
;
79
}
else
if
(errno == ECONNRESET) {
80
PLOG(
WARNING
) <<
getName
() <<
" SSL/TLS: Connection reset by peer (ECONNRESET)."
;
81
}
else
{
82
PLOG(
WARNING
) <<
getName
() <<
" SSL/TLS: Syscall error on write"
;
83
}
84
}
85
ret
= -1;
86
break
;
87
case
SSL_ERROR_SSL:
88
ssl_log
(
getName
() +
" SSL/TLS: Failed"
,
ssl_err
);
89
ret
= -1;
90
break
;
91
default
:
92
ssl_log
(
getName
() +
" SSL/TLS: Unexpected error"
,
ssl_err
);
93
errno = EIO;
94
ret
= -1;
95
break
;
96
}
97
}
98
}
99
100
return
ret
;
101
}
102
103
}
// namespace core::socket::stream::tls
core::socket::stream::SocketClient
Definition
SocketClient.h:48
core::socket::stream::tls
Definition
SocketReader.cpp:35
core
socket
stream
tls
SocketWriter.cpp
Generated on Mon Feb 10 2025 20:20:51 for SNode.C by
1.11.0