+ service_record *s1 = new service_record(&sset, "test-service-1", service_type_t::INTERNAL, {});
+ service_record *s2 = new service_record(&sset, "test-service-2", service_type_t::INTERNAL, {{s1, REG}});
+ service_record *s3 = new service_record(&sset, "test-service-3", service_type_t::INTERNAL, {{s2, REG}});
+ s2->set_auto_restart(true);
+ sset.add_service(s1);
+ sset.add_service(s2);
+ sset.add_service(s3);
+
+ // Pin s3:
+ s3->pin_start();
+
+ // Start all three services:
+ sset.start_service(s3);
+
+ assert(s3->get_state() == service_state_t::STARTED);
+ assert(s2->get_state() == service_state_t::STARTED);
+ assert(s1->get_state() == service_state_t::STARTED);
+
+ // Issue force stop to s2:
+ s2->stop(true);
+ s2->forced_stop();
+ sset.process_queues();
+
+ // s3 should remain started due to pin, but s1 and s2 are released and go STOPPING:
+ assert(s3->get_state() == service_state_t::STARTED);
+ assert(s2->get_state() == service_state_t::STOPPING);
+ assert(s1->get_state() == service_state_t::STOPPING);
+
+ // If we now issue start, s2 still needs to stop (due to force stop):
+ s3->start(true);
+ sset.process_queues();
+
+ assert(s3->get_state() == service_state_t::STARTED);
+ assert(s2->get_state() == service_state_t::STOPPING);
+ assert(s1->get_state() == service_state_t::STARTED);
+
+ // When we unpin, s2 should STOP; s3 must stop as a result; s1 is released and so also stops:
+ s3->unpin();
+
+ assert(s3->get_state() == service_state_t::STOPPED);
+ assert(s2->get_state() == service_state_t::STOPPED);
+ assert(s1->get_state() == service_state_t::STOPPED);
+}
+
+// Test that service pinned started is released when stop issued and stops when unpinned
+void test_pin4()
+{
+ service_set sset;
+