@@ -312,7 +312,7 @@ impl Daemon {
312312 info!( "upgrading packages" ) ;
313313 let _ = crate :: release:: package_upgrade( |event| {
314314 let _ = dbus_tx. send( SignalEvent :: Upgrade ( event) ) ;
315- } ) ;
315+ } ) . await ;
316316
317317 info!( "packages upgraded" ) ;
318318 }
@@ -762,6 +762,7 @@ impl Daemon {
762762 ( "status" , "sub_status" ) ,
763763 |_ctx : & mut Context , daemon : & mut Daemon , _inputs : ( ) | {
764764 let status = daemon. shared_state . status . load ( Ordering :: SeqCst ) as u8 ;
765+ #[ allow( clippy:: unnecessary_cast) ]
765766 let sub_status = daemon. shared_state . sub_status . load ( Ordering :: SeqCst ) as u8 ;
766767 Ok ( ( status, sub_status) )
767768 } ,
@@ -804,129 +805,137 @@ impl Daemon {
804805
805806 loop {
806807 let _ = connection. process ( std:: time:: Duration :: from_millis ( 500 ) ) ;
807- let mut lock = cr. lock ( ) . unwrap ( ) ;
808- let daemon: & mut Daemon = lock. data_mut ( & path) . unwrap ( ) ;
809808
810- if shutdown_triggered {
811- break Ok ( ( ) ) ;
812- }
809+ let ( perform_upgrade , needs_cancel , shared_state ) = {
810+ let mut lock = cr . lock ( ) . unwrap ( ) ;
811+ let daemon : & mut Daemon = lock . data_mut ( & path ) . unwrap ( ) ;
813812
814- if !daemon. last_known . development {
815- if let ReleaseCheck :: NotFound = daemon. release_check {
816- shutdown_triggered = true ;
813+ if shutdown_triggered {
814+ break Ok ( ( ) ) ;
817815 }
818- }
819816
820- if daemon. perform_upgrade {
821- let mut packages = vec ! [ "pop-upgrade" , "libpop-upgrade-gtk" ] ;
822-
823- if let Ok ( ( _, mut policies) ) =
824- AptCache :: new ( ) . policy ( & [ "libpop-upgrade-gtk-dev" ] ) . await
825- {
826- if let Some ( policy) = policies. next ( ) . await {
827- if policy. installed != "(none)" {
828- packages. push ( "libpop-upgrade-gtk-dev" ) ;
829- }
817+ if !daemon. last_known . development {
818+ if let ReleaseCheck :: NotFound = daemon. release_check {
819+ shutdown_triggered = true ;
830820 }
831821 }
832822
833- self_upgrade ( & packages) . await ;
834- }
823+ let perform_upgrade = daemon. perform_upgrade ;
824+
825+ let needs_cancel = sighandler:: status ( ) . is_some_and ( |status| {
826+ info ! ( "received a '{}' signal" , status) ;
827+ matches ! ( status, sighandler:: Signal :: Terminate | sighandler:: Signal :: TermStop )
828+ } ) ;
835829
836- if let Some ( status) = sighandler:: status ( ) {
837- info ! ( "received a '{}' signal" , status) ;
830+ let shared_state = daemon. shared_state . clone ( ) ;
838831
839- use sighandler:: Signal :: { TermStop , Terminate } ;
832+ while let Ok ( fg_event) = fg_receiver. try_recv ( ) {
833+ match fg_event {
834+ FgEvent :: SetUpgradeState ( result, action, from, to) => {
835+ if result. is_ok ( ) {
836+ info ! ( "setting release upgrade state" ) ;
837+ let state = ReleaseUpgradeState { action, from, to } ;
838+ daemon. release_upgrade = Some ( state) ;
839+ }
840840
841- match status {
842- Terminate | TermStop => {
843- info ! ( "stopping daemon" ) ;
844- daemon. cancel ( ) . await ;
841+ let ( status, why) = result_signal ( result. as_ref ( ) ) ;
845842
846- shutdown_triggered = true ;
843+ daemon. last_known . release_upgrade = result;
844+
845+ Self :: send_signal_message ( & connection, {
846+ Self :: signal_message ( signals:: RELEASE_RESULT ) . append2 ( status, why)
847+ } )
848+ }
847849 }
848- _ => ( ) ,
849850 }
850- }
851851
852- while let Ok ( fg_event) = fg_receiver. try_recv ( ) {
853- match fg_event {
854- FgEvent :: SetUpgradeState ( result, action, from, to) => {
855- if result. is_ok ( ) {
856- info ! ( "setting release upgrade state" ) ;
857- let state = ReleaseUpgradeState { action, from, to } ;
858- daemon. release_upgrade = Some ( state) ;
852+ while let Ok ( dbus_event) = receiver. try_recv ( ) {
853+ debug ! ( "Sending DBus Event: {:#?}" , dbus_event) ;
854+
855+ Self :: send_signal_message ( & connection, {
856+ match & dbus_event {
857+ SignalEvent :: RecoveryUpgradeEvent ( _)
858+ | SignalEvent :: RecoveryUpgradeResult ( _)
859+ | SignalEvent :: ReleaseUpgradeEvent ( _)
860+ | SignalEvent :: Upgrade ( _) => info ! ( "{}" , dbus_event) ,
861+ _ => ( ) ,
859862 }
860863
861- let ( status, why) = result_signal ( result. as_ref ( ) ) ;
864+ match dbus_event {
865+ SignalEvent :: FetchResult ( result) => {
866+ let ( status, why) = result_signal ( result. as_ref ( ) ) ;
867+ let message = Self :: signal_message ( signals:: PACKAGE_FETCH_RESULT )
868+ . append2 ( status, why) ;
862869
863- daemon. last_known . release_upgrade = result;
870+ daemon. last_known . fetch = result;
871+ message
872+ }
873+ SignalEvent :: Fetched ( name, completed, total) => Self :: signal_message (
874+ signals:: PACKAGE_FETCHED ,
875+ )
876+ . append3 ( name. as_str ( ) , completed, total) ,
877+ SignalEvent :: Fetching ( name) => {
878+ Self :: signal_message ( signals:: PACKAGE_FETCHING )
879+ . append1 ( name. as_str ( ) )
880+ }
881+ SignalEvent :: NoConnection => {
882+ Self :: signal_message ( signals:: NO_CONNECTION )
883+ }
884+ SignalEvent :: RecoveryDownloadProgress ( progress, total) => {
885+ daemon
886+ . shared_state
887+ . fetching_state
888+ . store ( FetchState :: new ( progress, total) , Ordering :: SeqCst ) ;
889+ Self :: signal_message ( signals:: RECOVERY_DOWNLOAD_PROGRESS )
890+ . append2 ( progress, total)
891+ }
892+ SignalEvent :: RecoveryUpgradeEvent ( event) => {
893+ daemon. shared_state . sub_status . store ( event as u8 , Ordering :: SeqCst ) ;
894+ Self :: signal_message ( signals:: RECOVERY_EVENT ) . append1 ( event as u8 )
895+ }
896+ SignalEvent :: RecoveryUpgradeResult ( result) => {
897+ let ( status, why) = result_signal ( result. as_ref ( ) ) ;
898+ let message = Self :: signal_message ( signals:: RECOVERY_RESULT )
899+ . append2 ( status, why) ;
864900
865- Self :: send_signal_message ( & connection, {
866- Self :: signal_message ( signals:: RELEASE_RESULT ) . append2 ( status, why)
867- } )
868- }
901+ daemon. last_known . recovery_upgrade = result;
902+ message
903+ }
904+ SignalEvent :: ReleaseUpgradeEvent ( event) => {
905+ Self :: signal_message ( signals:: RELEASE_EVENT ) . append1 ( event as u8 )
906+ }
907+ SignalEvent :: Upgrade ( ref event) => {
908+ Self :: signal_message ( signals:: PACKAGE_UPGRADE )
909+ . append1 ( event. clone ( ) . into_dbus_map ( ) )
910+ }
911+ }
912+ } ) ;
869913 }
870- }
871-
872- while let Ok ( dbus_event) = receiver. try_recv ( ) {
873- debug ! ( "Sending DBus Event: {:#?}" , dbus_event) ;
874914
875- Self :: send_signal_message ( & connection, {
876- match & dbus_event {
877- SignalEvent :: RecoveryUpgradeEvent ( _)
878- | SignalEvent :: RecoveryUpgradeResult ( _)
879- | SignalEvent :: ReleaseUpgradeEvent ( _)
880- | SignalEvent :: Upgrade ( _) => info ! ( "{}" , dbus_event) ,
881- _ => ( ) ,
882- }
883-
884- match dbus_event {
885- SignalEvent :: FetchResult ( result) => {
886- let ( status, why) = result_signal ( result. as_ref ( ) ) ;
887- let message = Self :: signal_message ( signals:: PACKAGE_FETCH_RESULT )
888- . append2 ( status, why) ;
915+ ( perform_upgrade, needs_cancel, shared_state)
916+ } ;
917+ // Lock is dropped here
889918
890- daemon. last_known . fetch = result;
891- message
892- }
893- SignalEvent :: Fetched ( name, completed, total) => Self :: signal_message (
894- signals:: PACKAGE_FETCHED ,
895- )
896- . append3 ( name. as_str ( ) , completed, total) ,
897- SignalEvent :: Fetching ( name) => {
898- Self :: signal_message ( signals:: PACKAGE_FETCHING ) . append1 ( name. as_str ( ) )
899- }
900- SignalEvent :: NoConnection => Self :: signal_message ( signals:: NO_CONNECTION ) ,
901- SignalEvent :: RecoveryDownloadProgress ( progress, total) => {
902- daemon
903- . shared_state
904- . fetching_state
905- . store ( FetchState :: new ( progress, total) , Ordering :: SeqCst ) ;
906- Self :: signal_message ( signals:: RECOVERY_DOWNLOAD_PROGRESS )
907- . append2 ( progress, total)
908- }
909- SignalEvent :: RecoveryUpgradeEvent ( event) => {
910- daemon. shared_state . sub_status . store ( event as u8 , Ordering :: SeqCst ) ;
911- Self :: signal_message ( signals:: RECOVERY_EVENT ) . append1 ( event as u8 )
912- }
913- SignalEvent :: RecoveryUpgradeResult ( result) => {
914- let ( status, why) = result_signal ( result. as_ref ( ) ) ;
915- let message =
916- Self :: signal_message ( signals:: RECOVERY_RESULT ) . append2 ( status, why) ;
919+ if perform_upgrade {
920+ let mut packages = vec ! [ "pop-upgrade" , "libpop-upgrade-gtk" ] ;
917921
918- daemon. last_known . recovery_upgrade = result;
919- message
920- }
921- SignalEvent :: ReleaseUpgradeEvent ( event) => {
922- Self :: signal_message ( signals:: RELEASE_EVENT ) . append1 ( event as u8 )
923- }
924- SignalEvent :: Upgrade ( ref event) => {
925- Self :: signal_message ( signals:: PACKAGE_UPGRADE )
926- . append1 ( event. clone ( ) . into_dbus_map ( ) )
922+ if let Ok ( ( _, mut policies) ) =
923+ AptCache :: new ( ) . policy ( & [ "libpop-upgrade-gtk-dev" ] ) . await
924+ {
925+ if let Some ( policy) = policies. next ( ) . await {
926+ if policy. installed != "(none)" {
927+ packages. push ( "libpop-upgrade-gtk-dev" ) ;
927928 }
928929 }
929- } ) ;
930+ }
931+
932+ self_upgrade ( & packages) . await ;
933+ }
934+
935+ if needs_cancel {
936+ info ! ( "stopping daemon" ) ;
937+ cancel_shutdown ( & shared_state) . await ;
938+ shutdown_triggered = true ;
930939 }
931940 }
932941 }
@@ -986,30 +995,7 @@ impl Daemon {
986995 Ok ( ( ) )
987996 }
988997
989- async fn cancel ( & mut self ) {
990- if self . shared_state . release_upgrade_began . load ( Ordering :: SeqCst ) {
991- info ! ( "cannot cancel a release upgrade that's now ongoing" ) ;
992- return ;
993- }
994-
995- info ! ( "canceling a process which is in progress" ) ;
996-
997- // Grab the active task shutdown notifier.
998- let mut shutdown = self . shared_state . shutdown . lock ( ) . await ;
999-
1000- // Initiate shutdown of any background tasks.
1001- info ! ( "sending shutdown signal" ) ;
1002- let _res = shutdown. trigger_shutdown ( ( ) ) ;
1003-
1004- // Wait for active tasks to complete before returning.
1005- info ! ( "waiting for shutdown to complete" ) ;
1006- shutdown. wait_shutdown_complete ( ) . await ;
1007-
1008- // Insert a new shutdown notifier so it can be reused.
1009- * shutdown = Shutdown :: new ( ) ;
1010-
1011- info ! ( "canceled running processes" ) ;
1012- }
998+ async fn cancel ( & mut self ) { cancel_shutdown ( & self . shared_state ) . await ; }
1013999
10141000 fn recovery_upgrade_file ( & mut self , path : & str ) -> anyhow:: Result < ( ) > {
10151001 info ! ( "using {} to upgrade the recovery partition" , path) ;
@@ -1204,6 +1190,27 @@ fn dismissed_by_timestamp(timestamp: i64) -> Result<(), String> {
12041190 . map_err ( |why| format ! ( "install timestamp write: {}" , why) )
12051191}
12061192
1193+ async fn cancel_shutdown ( shared_state : & SharedState ) {
1194+ if shared_state. release_upgrade_began . load ( Ordering :: SeqCst ) {
1195+ info ! ( "cannot cancel a release upgrade that's now ongoing" ) ;
1196+ return ;
1197+ }
1198+
1199+ info ! ( "canceling a process which is in progress" ) ;
1200+
1201+ let mut shutdown = shared_state. shutdown . lock ( ) . await ;
1202+
1203+ info ! ( "sending shutdown signal" ) ;
1204+ let _res = shutdown. trigger_shutdown ( ( ) ) ;
1205+
1206+ info ! ( "waiting for shutdown to complete" ) ;
1207+ shutdown. wait_shutdown_complete ( ) . await ;
1208+
1209+ * shutdown = Shutdown :: new ( ) ;
1210+
1211+ info ! ( "canceled running processes" ) ;
1212+ }
1213+
12071214/// Installs packages in background, ensuring that the process continues
12081215/// even if the daemon is restarted
12091216async fn self_upgrade ( packages : & [ & str ] ) {
0 commit comments