Skip to content

Commit 832328c

Browse files
committed
Merge tag 'ata-6.6-final' of git://git.kernel.org/pub/scm/linux/kernel/git/dlemoal/libata
Pull ATA fix from Damien Le Moal: "A single patch to fix a regression introduced by the recent suspend/resume fixes. The regression is that ATA disks are not stopped on system shutdown, which is not recommended and increases the disks SMART counters for unclean power off events. This patch fixes this by refining the recent rework of the scsi device manage_xxx flags" * tag 'ata-6.6-final' of git://git.kernel.org/pub/scm/linux/kernel/git/dlemoal/libata: scsi: sd: Introduce manage_shutdown device flag
2 parents a78a67f + 24eca2d commit 832328c

File tree

4 files changed

+58
-7
lines changed

4 files changed

+58
-7
lines changed

drivers/ata/libata-scsi.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1053,10 +1053,11 @@ int ata_scsi_dev_config(struct scsi_device *sdev, struct ata_device *dev)
10531053

10541054
/*
10551055
* Ask the sd driver to issue START STOP UNIT on runtime suspend
1056-
* and resume only. For system level suspend/resume, devices
1057-
* power state is handled directly by libata EH.
1056+
* and resume and shutdown only. For system level suspend/resume,
1057+
* devices power state is handled directly by libata EH.
10581058
*/
10591059
sdev->manage_runtime_start_stop = true;
1060+
sdev->manage_shutdown = true;
10601061
}
10611062

10621063
/*

drivers/firewire/sbp2.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1521,6 +1521,7 @@ static int sbp2_scsi_slave_configure(struct scsi_device *sdev)
15211521
if (sbp2_param_exclusive_login) {
15221522
sdev->manage_system_start_stop = true;
15231523
sdev->manage_runtime_start_stop = true;
1524+
sdev->manage_shutdown = true;
15241525
}
15251526

15261527
if (sdev->type == TYPE_ROM)

drivers/scsi/sd.c

Lines changed: 36 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -209,7 +209,8 @@ manage_start_stop_show(struct device *dev,
209209

210210
return sysfs_emit(buf, "%u\n",
211211
sdp->manage_system_start_stop &&
212-
sdp->manage_runtime_start_stop);
212+
sdp->manage_runtime_start_stop &&
213+
sdp->manage_shutdown);
213214
}
214215
static DEVICE_ATTR_RO(manage_start_stop);
215216

@@ -275,6 +276,35 @@ manage_runtime_start_stop_store(struct device *dev,
275276
}
276277
static DEVICE_ATTR_RW(manage_runtime_start_stop);
277278

279+
static ssize_t manage_shutdown_show(struct device *dev,
280+
struct device_attribute *attr, char *buf)
281+
{
282+
struct scsi_disk *sdkp = to_scsi_disk(dev);
283+
struct scsi_device *sdp = sdkp->device;
284+
285+
return sysfs_emit(buf, "%u\n", sdp->manage_shutdown);
286+
}
287+
288+
static ssize_t manage_shutdown_store(struct device *dev,
289+
struct device_attribute *attr,
290+
const char *buf, size_t count)
291+
{
292+
struct scsi_disk *sdkp = to_scsi_disk(dev);
293+
struct scsi_device *sdp = sdkp->device;
294+
bool v;
295+
296+
if (!capable(CAP_SYS_ADMIN))
297+
return -EACCES;
298+
299+
if (kstrtobool(buf, &v))
300+
return -EINVAL;
301+
302+
sdp->manage_shutdown = v;
303+
304+
return count;
305+
}
306+
static DEVICE_ATTR_RW(manage_shutdown);
307+
278308
static ssize_t
279309
allow_restart_show(struct device *dev, struct device_attribute *attr, char *buf)
280310
{
@@ -607,6 +637,7 @@ static struct attribute *sd_disk_attrs[] = {
607637
&dev_attr_manage_start_stop.attr,
608638
&dev_attr_manage_system_start_stop.attr,
609639
&dev_attr_manage_runtime_start_stop.attr,
640+
&dev_attr_manage_shutdown.attr,
610641
&dev_attr_protection_type.attr,
611642
&dev_attr_protection_mode.attr,
612643
&dev_attr_app_tag_own.attr,
@@ -3819,8 +3850,10 @@ static void sd_shutdown(struct device *dev)
38193850
sd_sync_cache(sdkp, NULL);
38203851
}
38213852

3822-
if (system_state != SYSTEM_RESTART &&
3823-
sdkp->device->manage_system_start_stop) {
3853+
if ((system_state != SYSTEM_RESTART &&
3854+
sdkp->device->manage_system_start_stop) ||
3855+
(system_state == SYSTEM_POWER_OFF &&
3856+
sdkp->device->manage_shutdown)) {
38243857
sd_printk(KERN_NOTICE, sdkp, "Stopping disk\n");
38253858
sd_start_stop_device(sdkp, 0);
38263859
}

include/scsi/scsi_device.h

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -162,8 +162,24 @@ struct scsi_device {
162162
* core. */
163163
unsigned int eh_timeout; /* Error handling timeout */
164164

165-
bool manage_system_start_stop; /* Let HLD (sd) manage system start/stop */
166-
bool manage_runtime_start_stop; /* Let HLD (sd) manage runtime start/stop */
165+
/*
166+
* If true, let the high-level device driver (sd) manage the device
167+
* power state for system suspend/resume (suspend to RAM and
168+
* hibernation) operations.
169+
*/
170+
bool manage_system_start_stop;
171+
172+
/*
173+
* If true, let the high-level device driver (sd) manage the device
174+
* power state for runtime device suspand and resume operations.
175+
*/
176+
bool manage_runtime_start_stop;
177+
178+
/*
179+
* If true, let the high-level device driver (sd) manage the device
180+
* power state for system shutdown (power off) operations.
181+
*/
182+
bool manage_shutdown;
167183

168184
unsigned removable:1;
169185
unsigned changed:1; /* Data invalid due to media change */

0 commit comments

Comments
 (0)