@@ -1248,22 +1248,22 @@ func (dn *Daemon) update(oldConfig, newConfig *mcfgv1.MachineConfig, skipCertifi
12481248 }
12491249 }
12501250 }()
1251- }
12521251
1253- // Set password hash
1254- if err := dn .SetPasswordHash (newIgnConfig .Passwd .Users , oldIgnConfig .Passwd .Users ); err != nil {
1255- return err
1256- }
1252+ // Set password hash
1253+ if err := dn .SetPasswordHash (newIgnConfig .Passwd .Users , oldIgnConfig .Passwd .Users ); err != nil {
1254+ return err
1255+ }
12571256
1258- defer func () {
1259- if retErr != nil {
1260- if err := dn .SetPasswordHash (oldIgnConfig .Passwd .Users , newIgnConfig .Passwd .Users ); err != nil {
1261- errs := kubeErrs .NewAggregate ([]error {err , retErr })
1262- retErr = fmt .Errorf ("error rolling back password hash updates: %w" , errs )
1263- return
1257+ defer func () {
1258+ if retErr != nil {
1259+ if err := dn .SetPasswordHash (oldIgnConfig .Passwd .Users , newIgnConfig .Passwd .Users ); err != nil {
1260+ errs := kubeErrs .NewAggregate ([]error {err , retErr })
1261+ retErr = fmt .Errorf ("error rolling back password hash updates: %w" , errs )
1262+ return
1263+ }
12641264 }
1265- }
1266- }()
1265+ }()
1266+ }
12671267
12681268 if dn .os .IsCoreOSVariant () {
12691269 coreOSDaemon := CoreOSDaemon {dn }
@@ -2439,7 +2439,21 @@ func (dn *Daemon) atomicallyWriteSSHKey(authKeyPath, keys string) error {
24392439 return nil
24402440}
24412441
2442- // Set a given PasswdUser's Password Hash
2442+ func getUserPasswordHash (user string ) (string , error ) {
2443+ shadowOut , err := exec .Command ("getent" , "shadow" , user ).CombinedOutput ()
2444+ if err != nil {
2445+ return "" , fmt .Errorf ("Failed to check password hash for %s: %w" , user , err )
2446+ }
2447+ shadowSlice := strings .SplitN (strings .TrimSpace (string (shadowOut )), ":" , 3 )
2448+ if len (shadowSlice ) >= 2 {
2449+ return shadowSlice [1 ], nil
2450+ }
2451+ return "" , nil
2452+
2453+ }
2454+
2455+ // SetPasswordHash updates the password for each user in newUsers, skipping
2456+ // users whose password already matches the desired configuration.
24432457func (dn * Daemon ) SetPasswordHash (newUsers , oldUsers []ign3types.PasswdUser ) error {
24442458 // confirm that user exits
24452459 klog .Info ("Checking if absent users need to be disconfigured" )
@@ -2464,6 +2478,15 @@ func (dn *Daemon) SetPasswordHash(newUsers, oldUsers []ign3types.PasswdUser) err
24642478 pwhash = * u .PasswordHash
24652479 }
24662480
2481+ // Check if hash update is needed. Skip if not.
2482+ currentHash , err := getUserPasswordHash (u .Name )
2483+ if err != nil {
2484+ return err
2485+ }
2486+ if currentHash == pwhash {
2487+ continue
2488+ }
2489+
24672490 if out , err := exec .Command ("usermod" , "-p" , pwhash , u .Name ).CombinedOutput (); err != nil {
24682491 return fmt .Errorf ("Failed to reset password for %s: %s:%w" , u .Name , out , err )
24692492 }
0 commit comments