src/​examples/​cpp03/​local/​connect_pair.​cppsrc/​examples/​cpp11/​local/​connect_pair.​cpp
1 /​/​1 /​/​
2 /​/​·​connect_pair.​cpp2 /​/​·​connect_pair.​cpp
3 /​/​·​~~~~~~~~~~~~~~~~3 /​/​·​~~~~~~~~~~~~~~~~
4 /​/​4 /​/​
5 /​/​·​Copyright·​(c)​·​2003-​2023·​Christopher·​M.​·​Kohlhoff·​(chris·​at·​kohlhoff·​dot·​com)​5 /​/​·​Copyright·​(c)​·​2003-​2023·​Christopher·​M.​·​Kohlhoff·​(chris·​at·​kohlhoff·​dot·​com)​
6 /​/​6 /​/​
7 /​/​·​Distributed·​under·​the·​Boost·​Software·​License,​·​Version·​1.​0.​·​(See·​accompanying7 /​/​·​Distributed·​under·​the·​Boost·​Software·​License,​·​Version·​1.​0.​·​(See·​accompanying
8 /​/​·​file·​LICENSE_1_0.​txt·​or·​copy·​at·​http:​/​/​www.​boost.​org/​LICENSE_1_0.​txt)​8 /​/​·​file·​LICENSE_1_0.​txt·​or·​copy·​at·​http:​/​/​www.​boost.​org/​LICENSE_1_0.​txt)​
9 /​/​9 /​/​
10 10
11 #include·​<array>
11 #include·​<iostream>12 #include·​<iostream>
12 #include·​<string>13 #include·​<string>
13 #include·​<cctype>14 #include·​<cctype>
14 #include·​<asio.​hpp>15 #include·​<asio.​hpp>
15 #include·​<boost/​array.​hpp>
16 #include·​<boost/​bind/​bind.​hpp>
17 16
18 #if·​defined(ASIO_HAS_LOCA​L_SOCKETS)​17 #if·​defined(ASIO_HAS_LOCA​L_SOCKETS)​
19 18
20 using·​asio:​:​local:​:​stream_protocol;​19 using·​asio:​:​local:​:​stream_protocol;​
21 20
22 class·​uppercase_filter21 class·​uppercase_filter
23 {22 {
24 public:​23 public:​
25 ··​uppercase_filter(asio​:​:​io_context&·io_context)​24 ··​uppercase_filter(stre​am_protocol:​:​socket·sock)​
26 ····​:​·​local_socket(io_context)​25 ····​:​·​local_socket(std:​:​move(sock)​)​
27 ··​{26 ··​{
27 ····​read()​;​
28 ··​}28 ··​}
29 29
30 ··stream_protocol:​:​socket&·socket()​30 private:​
31 ··​void·​read()​
31 ··​{32 ··​{
32 ····​return·​local_socket;​
33 ··​}
34
35 ··​void·​start()​
36 ··​{
37 ····​/​/​·​Wait·​for·​request.​
38 ····​local_socket.​async_read_some(asio:​:​buffer(data_)​,​33 ····​local_socket.​async_read_some(asio:​:​buffer(data_)​,​
39 ········boost:​:​bind(&uppercase_filte​r:​:​handle_read,​34 ········[this](std:​:​error_code·ec,​·std:​:​size_t·size)​
40 ··········this,​·asio:​:​placeholders:​:​error,​35 ········{
41 ··········asio:​:​placeholders:​:​bytes_transferred)​)​;​36 ··········​if·(!ec)​
42 ··}37 ··········{
38 ············​/​/​·​Compute·​result.​
39 ············​for·​(std:​:​size_t·​i·​=·​0;​·​i·​<·​size;​·​++i)​
40 ··············​data_[i]·​=·​std:​:​toupper(data_[i])​;​
43 41
44 private:​42 ············/​/​·Send·result.​
45 ··void·handle_read(const·asio:​:​error_code&·ec,​·std:​:​size_t·size)​43 ············write(size)​;​
46 ··{44 ··········}
47 ····if·(!ec)​45 ··········else
48 ····​{46 ··········​{
49 ······/​/​·Compute·result.​47 ············throw·asio:​:​system_error(ec)​;​
50 ······for·(std:​:​size_t·i·=·0;​·i·<·size;​·++i)​48 ··········}
51 ········data_[i]·=·std:​:​toupper(data_[i])​;​49 ········})​;​
52
53 ······/​/​·Send·result.​
54 ······asio:​:​async_write(socket_,​·asio:​:​buffer(data_,​·size)​,​
55 ··········boost:​:​bind(&uppercase_filte​r:​:​handle_write,​
56 ············this,​·asio:​:​placeholders:​:​error)​)​;​
57 ····}
58 ····else
59 ····{
60 ······throw·asio:​:​system_error(ec)​;​
61 ····}
62 ··​}50 ··​}
63 51
64 ··​void·handle_write(const·asio:​:​error_code&·ec)​52 ··​void·​write(std:​:​size_t·size)​
65 ··​{53 ··​{
66 ····​if·(!ec)​54 ····asio:​:​async_write(socket_,​·asio:​:​buffer(data_,​·size)​,​
67 ····{55 ········[this](std:​:​error_code·ec,​·std:​:​size_t·/​*size*/​)​
68 ······/​/​·Wait·for·request.​56 ········{
69 ······socket_.​async_read_some(asio:​:​buffer(data_)​,​57 ··········if·(!ec)​
70 ··········boost:​:​bind(&uppercase_filte​r:​:​handle_read,​58 ··········{
71 ············this,​·asio:​:​placeholders:​:​error,​59 ············/​/​·Wait·for·request.​
72 ············asio:​:​placeholders:​:​bytes_transferred)​)​;​60 ············​read()​;​
73 ····​}61 ··········​}
74 ····​else62 ··········​else
75 ····​{63 ··········​{
76 ······​throw·​asio:​:​system_error(ec)​;​64 ············​throw·​asio:​:​system_error(ec)​;​
77 ····​}65 ··········​}
66 ········​})​;​
78 ··​}67 ··​}
79 68
80 ··​stream_protocol:​:​socket·​local_socket;​69 ··​stream_protocol:​:​socket·​local_socket;​
81 ··boost:​:​array<char,​·​512>·​data_;​70 ··​std:​:​array<char,​·​512>·​data_;​
82 };​71 };​
83 72
84 void·​run(asio:​:​io_context*·​io_context)​
85 {
86 ··​try
87 ··​{
88 ····​io_context-​>run()​;​
89 ··​}
90 ··​catch·​(std:​:​exception&·​e)​
91 ··​{
92 ····​std:​:​cerr·​<<·​"Exception·​in·​thread:​·​"·​<<·​e.​what()​·​<<·​"\n";​
93 ····​std:​:​exit(1)​;​
94 ··​}
95 }
96
97 int·​main()​73 int·​main()​
98 {74 {
99 ··​try75 ··​try
100 ··​{76 ··​{
101 ····​asio:​:​io_context·​io_context;​77 ····​asio:​:​io_context·​io_context;​
102 78
103 ····​/​/​·​Create·filter·​and·establish·a·connection·to·it.​79 ····​/​/​·​Create·a·connected·pair·and·pass·one·end·to·a·filter.​
104 ····uppercase_filter·filter(io_context)​;​
105 ····​stream_protocol:​:​socket·​socket(io_context)​;​80 ····​stream_protocol:​:​socket·​socket(io_context)​;​
106 ····asio:​:​local:​:​connect_pair(socket,​·​filter.​socket()​)​;​81 ····​stream_protocol:​:​socket·​filter_socket(io_cont​ext)​;​
107 ····​filter.​start()​;​82 ····asio:​:​local:​:​connect_pair(socket,​·​filter_socket)​;​
83 ····​uppercase_filter·​filter(std:​:​move(filter_socket)​)​;​
108 84
109 ····​/​/​·​The·​io_context·​runs·​in·​a·​background·​thread·​to·​perform·​filtering.​85 ····​/​/​·​The·​io_context·​runs·​in·​a·​background·​thread·​to·​perform·​filtering.​
110 ····​asio:​:​thread·​thread(boost:​:​bind(run,​·&io_context)​)​;​86 ····​asio:​:​thread·​thread(
87 ········​[&io_context]()​
88 ········​{
89 ··········​try
90 ··········​{
91 ············​io_context.​run()​;​
92 ··········​}
93 ··········​catch·​(std:​:​exception&·​e)​
94 ··········​{
95 ············​std:​:​cerr·​<<·​"Exception·​in·​thread:​·​"·​<<·​e.​what()​·​<<·​"\n";​
96 ············​std:​:​exit(1)​;​
97 ··········​}
98 ········​})​;​
111 99
112 ····​for·​(;​;​)​100 ····​for·​(;​;​)​
113 ····​{101 ····​{
114 ······​/​/​·​Collect·​request·​from·​user.​102 ······​/​/​·​Collect·​request·​from·​user.​
115 ······​std:​:​cout·​<<·​"Enter·​a·​string:​·​";​103 ······​std:​:​cout·​<<·​"Enter·​a·​string:​·​";​
116 ······​std:​:​string·​request;​104 ······​std:​:​string·​request;​
117 ······​std:​:​getline(std:​:​cin,​·​request)​;​105 ······​std:​:​getline(std:​:​cin,​·​request)​;​
118 106
119 ······​/​/​·​Send·​request·​to·​filter.​107 ······​/​/​·​Send·​request·​to·​filter.​
120 ······​asio:​:​write(socket,​·​asio:​:​buffer(request)​)​;​108 ······​asio:​:​write(socket,​·​asio:​:​buffer(request)​)​;​
121 109
122 ······​/​/​·​Wait·​for·​reply·​from·​filter.​110 ······​/​/​·​Wait·​for·​reply·​from·​filter.​
123 ······​std:​:​vector<char>·​reply(request.​size()​)​;​111 ······​std:​:​vector<char>·​reply(request.​size()​)​;​
124 ······​asio:​:​read(socket,​·​asio:​:​buffer(reply)​)​;​112 ······​asio:​:​read(socket,​·​asio:​:​buffer(reply)​)​;​
125 113
126 ······​/​/​·​Show·​reply·​to·​user.​114 ······​/​/​·​Show·​reply·​to·​user.​
127 ······​std:​:​cout·​<<·​"Result:​·​";​115 ······​std:​:​cout·​<<·​"Result:​·​";​
128 ······​std:​:​cout.​write(&reply[0],​·​request.​size()​)​;​116 ······​std:​:​cout.​write(&reply[0],​·​request.​size()​)​;​
129 ······​std:​:​cout·​<<·​std:​:​endl;​117 ······​std:​:​cout·​<<·​std:​:​endl;​
130 ····​}118 ····​}
131 ··​}119 ··​}
132 ··​catch·​(std:​:​exception&·​e)​120 ··​catch·​(std:​:​exception&·​e)​
133 ··​{121 ··​{
134 ····​std:​:​cerr·​<<·​"Exception:​·​"·​<<·​e.​what()​·​<<·​"\n";​122 ····​std:​:​cerr·​<<·​"Exception:​·​"·​<<·​e.​what()​·​<<·​"\n";​
135 ····​std:​:​exit(1)​;​123 ····​std:​:​exit(1)​;​
136 ··​}124 ··​}
137 }125 }
138 126
139 #else·​/​/​·​defined(ASIO_HAS_LOCA​L_SOCKETS)​127 #else·​/​/​·​defined(ASIO_HAS_LOCA​L_SOCKETS)​
140 #·​error·​Local·​sockets·​not·​available·​on·​this·​platform.​128 #·​error·​Local·​sockets·​not·​available·​on·​this·​platform.​
141 #endif·​/​/​·​defined(ASIO_HAS_LOCA​L_SOCKETS)​129 #endif·​/​/​·​defined(ASIO_HAS_LOCA​L_SOCKETS)​