Merge lp:~thomas-voss/location-service/fix-race-with-timeout-handler into lp:location-service/trunk

Proposed by Thomas Voß
Status: Merged
Approved by: Thomas Voß
Approved revision: 265
Merged at revision: 267
Proposed branch: lp:~thomas-voss/location-service/fix-race-with-timeout-handler
Merge into: lp:location-service/trunk
Diff against target: 50 lines (+14/-7)
1 file modified
src/location_service/com/ubuntu/location/providers/gps/sntp_client.cpp (+14/-7)
To merge this branch: bzr merge lp:~thomas-voss/location-service/fix-race-with-timeout-handler
Reviewer Review Type Date Requested Status
Simon Fels Approve
Review via email: mp+302513@code.launchpad.net

Commit message

Make sure that we are not racing with the timeout handler.

Description of the change

Make sure that we are not racing with the timeout handler.

To post a comment you must log in.
Revision history for this message
Simon Fels (morphis) wrote :

LGTM

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'src/location_service/com/ubuntu/location/providers/gps/sntp_client.cpp'
2--- src/location_service/com/ubuntu/location/providers/gps/sntp_client.cpp 2016-03-03 15:59:00 +0000
3+++ src/location_service/com/ubuntu/location/providers/gps/sntp_client.cpp 2016-08-10 07:59:49 +0000
4@@ -109,13 +109,10 @@
5 timer.expires_from_now(boost::posix_time::milliseconds{timeout.count()});
6 timer.async_wait([&timed_out, &resolver, &socket](const boost::system::error_code& ec)
7 {
8- if (ec)
9- return;
10+ if (ec) return;
11
12 timed_out = true;
13-
14 resolver.cancel();
15- socket.shutdown(ip::udp::socket::shutdown_both);
16 socket.close();
17 });
18
19@@ -134,6 +131,13 @@
20 std::promise<void> promise_connect;
21 auto future_connect = promise_connect.get_future();
22
23+ // We are subject to a race here as the timeout handler might have been triggered
24+ // _before_ we have started connecting the socket. For that, we check whether we are
25+ // already past the deadline prior to establishing a connection. Once we are past this point,
26+ // the usual mechanisms for closed sockets kick in.
27+ if (timer.expires_at() <= boost::asio::deadline_timer::traits_type::now())
28+ throw std::runtime_error{"Timed out"};
29+
30 socket.async_connect(*it, [&promise_connect](const boost::system::error_code& ec)
31 {
32 if (ec)
33@@ -147,12 +151,15 @@
34 sntp::Packet packet;
35
36 Now before;
37- {
38+ {
39+ if (timer.expires_at() <= boost::asio::deadline_timer::traits_type::now())
40+ throw std::runtime_error{"Timed out"};
41+
42 packet = request(socket);
43 timer.cancel();
44
45- if (timed_out)
46- throw std::runtime_error("Operation timed out.");
47+ if (timer.expires_at() <= boost::asio::deadline_timer::traits_type::now())
48+ throw std::runtime_error{"Timed out"};
49 }
50 Now after;
51

Subscribers

People subscribed via source and target branches