Factor out ATA routines
authorDavid Zeuthen <zeuthen@gmail.com>
Tue, 23 Oct 2012 18:25:13 +0000 (14:25 -0400)
committerDavid Zeuthen <zeuthen@gmail.com>
Tue, 23 Oct 2012 18:25:13 +0000 (14:25 -0400)
Signed-off-by: David Zeuthen <zeuthen@gmail.com>
doc/udisks2-docs.xml
doc/udisks2-sections.txt
src/Makefile.am
src/udisksdaemontypes.h
src/udiskslinuxdriveata.c

index 97e5e63..01721f7 100644 (file)
       <xi:include href="xml/udisksprovider.xml"/>
       <xi:include href="xml/udiskscleanup.xml"/>
       <xi:include href="xml/udiskspersistentstore.xml"/>
+      <xi:include href="xml/udisksata.xml"/>
     </chapter>
     <chapter id="ref-daemon-monitoring">
       <title>State and Configuration</title>
index af9258a..8749579 100644 (file)
@@ -341,6 +341,14 @@ udisks_cleanup_get_type
 </SECTION>
 
 <SECTION>
+<FILE>udisksata</FILE>
+UDisksAtaCommandProtocol
+UDisksAtaCommandInput
+UDisksAtaCommandOutput
+udisks_ata_send_command_sync
+</SECTION>
+
+<SECTION>
 <FILE>udisksdaemonutil</FILE>
 udisks_decode_udev_string
 udisks_safe_append_to_object_path
index 25ca034..11543f9 100644 (file)
@@ -77,6 +77,7 @@ libudisks_daemon_la_SOURCES =                                         \
        udisksfstabmonitor.h            udisksfstabmonitor.c            \
        udiskscrypttabentry.h           udiskscrypttabentry.c           \
        udiskscrypttabmonitor.h         udiskscrypttabmonitor.c         \
+       udisksata.h                     udisksata.c                     \
        $(BUILT_SOURCES)                                                \
        $(NULL)
 
index c2290e5..858abce 100644 (file)
@@ -172,4 +172,25 @@ typedef enum
   UDISKS_LOG_LEVEL_ERROR
 } UDisksLogLevel;
 
+struct _UDisksAtaCommandOutput;
+typedef struct _UDisksAtaCommandOutput UDisksAtaCommandOutput;
+
+struct _UDisksAtaCommandInput;
+typedef struct _UDisksAtaCommandInput UDisksAtaCommandInput;
+
+/**
+ * UDisksAtaCommandProtocol:
+ * @UDISKS_ATA_COMMAND_PROTOCOL_NONE: Non-data
+ * @UDISKS_ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST: PIO Data-In
+ * @UDISKS_ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE: PIO Data-Out
+ *
+ * Enumeration used to specify the protocol of an ATA command
+ */
+typedef enum
+{
+  UDISKS_ATA_COMMAND_PROTOCOL_NONE,
+  UDISKS_ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST,
+  UDISKS_ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE
+} UDisksAtaCommandProtocol;
+
 #endif /* __UDISKS_DAEMON_TYPES_H__ */
index b9b735e..f37a09c 100644 (file)
 #include <sys/stat.h>
 #include <sys/ioctl.h>
 #include <fcntl.h>
-#include <linux/bsg.h>
-#include <scsi/scsi.h>
-#include <scsi/sg.h>
-#include <scsi/scsi_ioctl.h>
-#include <linux/cdrom.h>
 
 #include <pwd.h>
 #include <grp.h>
@@ -54,6 +49,7 @@
 #include "udisksbasejob.h"
 #include "udiskssimplejob.h"
 #include "udisksthreadedjob.h"
+#include "udisksata.h"
 
 /**
  * SECTION:udiskslinuxdriveata
@@ -1131,283 +1127,6 @@ handle_smart_selftest_start (UDisksDriveAta        *_drive,
 
 /* ---------------------------------------------------------------------------------------------------- */
 
-#define ATA_DEFAULT_COMMAND_TIMEOUT_MSEC (5 * 1000)
-
-typedef struct
-{
-  guint8  command;
-  guint8  feature;
-  guint8  count;
-  guint8  device;
-  guint32 lba;
-  gsize   buffer_size;
-  guchar *buffer;
-} AtaCommandInput;
-
-typedef struct
-{
-  guint8  error;
-  guint8  count;
-  guint8  device;
-  guint8  status;
-  guint32 lba;
-  gsize   buffer_size;
-  guchar *buffer;
-} AtaCommandOutput;
-
-typedef enum
-{
-  ATA_COMMAND_PROTOCOL_NONE,           /* Non-data */
-  ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST,  /* PIO Data-In */
-  ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE,  /* PIO Data-Out */
-} AtaCommandProtocol;
-
-static gboolean
-ata_send_command (gint                 fd,
-                  gint                 timeout_msec,
-                  AtaCommandProtocol   protocol,
-                  AtaCommandInput     *input,
-                  AtaCommandOutput    *output,
-                  GError             **error)
-{
-  struct sg_io_v4 io_v4;
-  uint8_t cdb[16];
-  gint cdb_len = 16;
-  uint8_t sense[32];
-  uint8_t *desc = sense+8;
-  gboolean use_ata12 = FALSE;
-  gboolean ret = FALSE;
-  gint rc;
-
-  g_return_val_if_fail (fd != -1, FALSE);
-  g_return_val_if_fail (timeout_msec == -1 || timeout_msec > 0, FALSE);
-  g_return_val_if_fail (/* protocol >= 0 && */ protocol <= 2, FALSE);
-  g_return_val_if_fail (input != NULL, FALSE);
-  g_return_val_if_fail (input->buffer_size == 0 || input->buffer != NULL, FALSE);
-  g_return_val_if_fail (output != NULL, FALSE);
-  g_return_val_if_fail (output->buffer_size == 0 || output->buffer != NULL, FALSE);
-  g_return_val_if_fail (error == NULL || *error == NULL, FALSE);
-
-  if (timeout_msec == -1)
-    timeout_msec = ATA_DEFAULT_COMMAND_TIMEOUT_MSEC;
-
-  /* zero outputs, even if returning an error */
-  output->error = 0;
-  output->count = 0;
-  output->device = 0;
-  output->status = 0;
-  output->lba = 0;
-  if (output->buffer != NULL)
-    memset (output->buffer, 0, output->buffer_size);
-
-  memset (cdb, 0, sizeof (cdb));
-
-  /* Prefer ATA PASS-THROUGH (16) to ATA PASS-THROUGH (12) since the op-code
-   * for the latter clashes with the MMC blank command.
-   *
-   * TODO: this is hard-coded to FALSE for now - should retry with the 12-byte
-   *       version only if the 16-byte version fails. But we don't do that
-   *       right now
-   */
-  use_ata12 = FALSE;
-
-  if (use_ata12)
-    {
-      /* Do not confuse optical drive firmware with ATA commands
-       * some drives are reported to blank CD-RWs because the op-code
-       * for ATA PASS-THROUGH (12) clashes with the MMC blank command.
-       *
-       * http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=556635
-       */
-      if (ioctl (fd, CDROM_GET_CAPABILITY, NULL) >= 0)
-        {
-          g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED,
-                       "Refusing to send ATA PASS-THROUGH (12) to optical drive");
-          goto out;
-        }
-
-      /*
-       * ATA Pass-Through 12 byte command, as described in
-       *
-       *  T10 04-262r8 ATA Command Pass-Through
-       *
-       * from http://www.t10.org/ftp/t10/document.04/04-262r8.pdf
-       */
-      cdb[0] = 0xa1;                        /* OPERATION CODE: 12 byte pass through */
-      switch (protocol)
-        {
-        case ATA_COMMAND_PROTOCOL_NONE:
-          cdb[1] = 3 << 1;                  /* PROTOCOL: Non-data */
-          cdb[2] = 0x20;                    /* OFF_LINE=0, CK_COND=1, T_DIR=0, BYT_BLOK=0, T_LENGTH=0 */
-          break;
-        case ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST:
-          cdb[1] = 4 << 1;                  /* PROTOCOL: PIO Data-In */
-          cdb[2] = 0x2e;                    /* OFF_LINE=0, CK_COND=1, T_DIR=1, BYT_BLOK=1, T_LENGTH=2 */
-          break;
-        case ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE:
-          cdb[1] = 5 << 1;                  /* PROTOCOL: PIO Data-Out */
-          cdb[2] = 0x26;                    /* OFF_LINE=0, CK_COND=1, T_DIR=0, BYT_BLOK=1, T_LENGTH=2 */
-          break;
-        default:
-          g_assert_not_reached ();
-          break;
-        }
-      cdb[3] = input->feature;              /* FEATURES */
-      cdb[4] = input->count;                /* SECTORS */
-      cdb[5] = (input->lba >>  0) & 0xff;   /* LBA LOW */
-      cdb[6] = (input->lba >>  8) & 0xff;   /* LBA MID */
-      cdb[7] = (input->lba >> 16) & 0xff;   /* LBA HIGH */
-      cdb[8] = input->device;               /* SELECT */
-      cdb[9] = input->command;              /* ATA COMMAND */
-      cdb_len = 12;
-    }
-  else
-    {
-      /*
-       * ATA Pass-Through 16 byte command, as described in
-       *
-       *  T10 04-262r8 ATA Command Pass-Through
-       *
-       * from http://www.t10.org/ftp/t10/document.04/04-262r8.pdf
-       */
-      cdb[0] = 0x85;                        /* OPERATION CODE: 16 byte pass through */
-      switch (protocol)
-        {
-        case ATA_COMMAND_PROTOCOL_NONE:
-          cdb[1] = 3 << 1;                  /* PROTOCOL: Non-data */
-          cdb[2] = 0x20;                    /* OFF_LINE=0, CK_COND=1, T_DIR=0, BYT_BLOK=0, T_LENGTH=0 */
-          break;
-        case ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST:
-          cdb[1] = 4 << 1;                  /* PROTOCOL: PIO Data-In */
-          cdb[2] = 0x2e;                    /* OFF_LINE=0, CK_COND=1, T_DIR=1, BYT_BLOK=1, T_LENGTH=2 */
-          break;
-        case ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE:
-          cdb[1] = 5 << 1;                  /* PROTOCOL: PIO Data-Out */
-          cdb[2] = 0x26;                    /* OFF_LINE=0, CK_COND=1, T_DIR=0, BYT_BLOK=1, T_LENGTH=2 */
-          break;
-        default:
-          g_assert_not_reached ();
-          break;
-        }
-      cdb[ 3] = (input->feature >>  8) & 0xff;   /* FEATURES */
-      cdb[ 4] = (input->feature >>  0) & 0xff;   /* FEATURES */
-      cdb[ 5] = (input->count >>  8) & 0xff;     /* SECTORS */
-      cdb[ 6] = (input->count >>  0) & 0xff;     /* SECTORS */
-      cdb[ 8] = (input->lba >> 16) & 0xff;       /* LBA HIGH */
-      cdb[10] = (input->lba >>  8) & 0xff;       /* LBA MID */
-      cdb[12] = (input->lba >>  0) & 0xff;       /* LBA LOW */
-      cdb[13] = input->device;                   /* SELECT */
-      cdb[14] = input->command;                  /* ATA COMMAND */
-      cdb_len = 16;
-    }
-
-  /* See http://sg.danny.cz/sg/sg_io.html and http://www.tldp.org/HOWTO/SCSI-Generic-HOWTO/index.html
-   * for detailed information about how the SG_IO ioctl work
-   */
-
-  memset (sense, 0, sizeof (sense));
-  memset (&io_v4, 0, sizeof (io_v4));
-  io_v4.guard = 'Q';
-  io_v4.protocol = BSG_PROTOCOL_SCSI;
-  io_v4.subprotocol = BSG_SUB_PROTOCOL_SCSI_CMD;
-  io_v4.request_len = cdb_len;
-  io_v4.request = (uintptr_t) cdb;
-  io_v4.max_response_len = sizeof (sense);
-  io_v4.response = (uintptr_t) sense;
-  io_v4.din_xfer_len = output->buffer_size;
-  io_v4.din_xferp = (uintptr_t) output->buffer;
-  io_v4.dout_xfer_len = input->buffer_size;
-  io_v4.dout_xferp = (uintptr_t) input->buffer;
-  if (timeout_msec == G_MAXINT)
-    io_v4.timeout = G_MAXUINT;
-  else
-    io_v4.timeout = timeout_msec;
-
-  rc = ioctl (fd, SG_IO, &io_v4);
-  if (rc != 0)
-    {
-      /* could be that the driver doesn't do version 4, try version 3 */
-      if (errno == EINVAL)
-        {
-          struct sg_io_hdr io_hdr;
-
-          memset(&io_hdr, 0, sizeof (struct sg_io_hdr));
-          io_hdr.interface_id = 'S';
-          io_hdr.cmdp = (unsigned char*) cdb;
-          io_hdr.cmd_len = cdb_len;
-          switch (protocol)
-            {
-            case ATA_COMMAND_PROTOCOL_NONE:
-              io_hdr.dxfer_direction = SG_DXFER_NONE;
-              break;
-
-            case ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST:
-              io_hdr.dxferp = output->buffer;
-              io_hdr.dxfer_len = output->buffer_size;
-              io_hdr.dxfer_direction = SG_DXFER_FROM_DEV;
-              break;
-
-            case ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE:
-              io_hdr.dxferp = input->buffer;
-              io_hdr.dxfer_len = input->buffer_size;
-              io_hdr.dxfer_direction = SG_DXFER_TO_DEV;
-              break;
-            }
-          io_hdr.sbp = sense;
-          io_hdr.mx_sb_len = sizeof (sense);
-          if (timeout_msec == G_MAXINT)
-            io_hdr.timeout = G_MAXUINT;
-          else
-            io_hdr.timeout = timeout_msec;
-
-          rc = ioctl(fd, SG_IO, &io_hdr);
-          if (rc != 0)
-            {
-              g_set_error (error, G_IO_ERROR, g_io_error_from_errno (errno),
-                           "SGIO v3 ioctl failed (v4 not supported): %m");
-              goto out;
-            }
-        }
-      else
-        {
-          g_set_error (error, G_IO_ERROR, g_io_error_from_errno (errno),
-                       "SGIO v4 ioctl failed: %m");
-          goto out;
-        }
-    }
-
-  if (!(sense[0] == 0x72 && desc[0] == 0x9 && desc[1] == 0x0c))
-    {
-      gchar *s = udisks_daemon_util_hexdump (sense, 32);
-      g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED,
-                   "Unexpected sense data returned:\n%s", s);
-      g_free (s);
-      goto out;
-    }
-
-  output->error = desc[3];
-  output->count = desc[5];
-  output->device = desc[12];
-  output->status = desc[13];
-  output->lba = (desc[11] << 16) | (desc[9] << 8) | desc[7];
-
-  /* TODO: be more exact with the error code perhaps? */
-  if (output->error != 0 || output->status & 0x01)
-    {
-      g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED,
-                   "ATA command failed: error=0x%02x count=0x%02x status=0x%02x",
-                   output->error, output->count, output->status);
-      goto out;
-    }
-
-  ret = TRUE;
-
- out:
-  return ret;
-}
-
-/* ---------------------------------------------------------------------------------------------------- */
-
 static gboolean
 handle_pm_get_state (UDisksDriveAta        *_drive,
                      GDBusMethodInvocation *invocation,
@@ -1489,14 +1208,14 @@ handle_pm_get_state (UDisksDriveAta        *_drive,
 
   {
     /* ATA8: 7.8 CHECK POWER MODE - E5h, Non-Data */
-    AtaCommandInput input = {.command = 0xe5};
-    AtaCommandOutput output = {0};
-    if (!ata_send_command (fd,
-                           -1,
-                           ATA_COMMAND_PROTOCOL_NONE,
-                           &input,
-                           &output,
-                           &error))
+    UDisksAtaCommandInput input = {.command = 0xe5};
+    UDisksAtaCommandOutput output = {0};
+    if (!udisks_ata_send_command_sync (fd,
+                                       -1,
+                                       UDISKS_ATA_COMMAND_PROTOCOL_NONE,
+                                       &input,
+                                       &output,
+                                       &error))
       {
         g_prefix_error (&error, "Error sending ATA command CHECK POWER MODE: ");
         g_dbus_method_invocation_take_error (invocation, error);
@@ -1620,14 +1339,14 @@ handle_pm_standby (UDisksDriveAta        *_drive,
 
   {
     /* ATA8: 7.55 STANDBY IMMEDIATE - E0h, Non-Data */
-    AtaCommandInput input = {.command = 0xe0};
-    AtaCommandOutput output = {0};
-    if (!ata_send_command (fd,
-                           -1,
-                           ATA_COMMAND_PROTOCOL_NONE,
-                           &input,
-                           &output,
-                           &error))
+    UDisksAtaCommandInput input = {.command = 0xe0};
+    UDisksAtaCommandOutput output = {0};
+    if (!udisks_ata_send_command_sync (fd,
+                                       -1,
+                                       UDISKS_ATA_COMMAND_PROTOCOL_NONE,
+                                       &input,
+                                       &output,
+                                       &error))
       {
         g_prefix_error (&error, "Error sending ATA command STANDBY IMMEDIATE: ");
         g_dbus_method_invocation_take_error (invocation, error);
@@ -1865,14 +1584,14 @@ apply_configuration_thread_func (gpointer user_data)
   if (data->ata_pm_standby != -1)
     {
       /* ATA8: 7.18 IDLE - E3h, Non-Data */
-      AtaCommandInput input = {.command = 0xe3, .count = data->ata_pm_standby};
-      AtaCommandOutput output = {0};
-      if (!ata_send_command (fd,
-                             -1,
-                             ATA_COMMAND_PROTOCOL_NONE,
-                             &input,
-                             &output,
-                             &error))
+      UDisksAtaCommandInput input = {.command = 0xe3, .count = data->ata_pm_standby};
+      UDisksAtaCommandOutput output = {0};
+      if (!udisks_ata_send_command_sync (fd,
+                                         -1,
+                                         UDISKS_ATA_COMMAND_PROTOCOL_NONE,
+                                         &input,
+                                         &output,
+                                         &error))
         {
           udisks_error ("Error sending ATA command IDLE (timeout=%d) to %s: %s (%s, %d)",
                         data->ata_pm_standby, device_file,
@@ -1893,19 +1612,19 @@ apply_configuration_thread_func (gpointer user_data)
       /* ATA8: 7.48 SET FEATURES - EFh, Non-Data
        *       7.48.6 Enable/disable the APM feature set
        */
-      AtaCommandInput input = {.command = 0xef, .feature = 0x05, .count = data->ata_apm_level};
-      AtaCommandOutput output = {0};
+      UDisksAtaCommandInput input = {.command = 0xef, .feature = 0x05, .count = data->ata_apm_level};
+      UDisksAtaCommandOutput output = {0};
       if (data->ata_apm_level == 0xff)
         {
           input.feature = 0x85;
           input.count = 0x00;
         }
-      if (!ata_send_command (fd,
-                             -1,
-                             ATA_COMMAND_PROTOCOL_NONE,
-                             &input,
-                             &output,
-                             &error))
+      if (!udisks_ata_send_command_sync (fd,
+                                         -1,
+                                         UDISKS_ATA_COMMAND_PROTOCOL_NONE,
+                                         &input,
+                                         &output,
+                                         &error))
         {
           udisks_error ("Error sending ATA command SET FEATURES, sub-command 0x%02x (ata_apm_level=%d) to %s: %s (%s, %d)",
                         input.feature, data->ata_apm_level, device_file,
@@ -1924,19 +1643,19 @@ apply_configuration_thread_func (gpointer user_data)
       /* ATA8: 7.48 SET FEATURES - EFh, Non-Data
        *       7.48.11 Enable/disable the AAM feature set
        */
-      AtaCommandInput input = {.command = 0xef, .feature = 0x42, .count = data->ata_aam_level};
-      AtaCommandOutput output = {0};
+      UDisksAtaCommandInput input = {.command = 0xef, .feature = 0x42, .count = data->ata_aam_level};
+      UDisksAtaCommandOutput output = {0};
       if (data->ata_apm_level == 0xff)
         {
           input.feature = 0xc2;
           input.count = 0x00;
         }
-      if (!ata_send_command (fd,
-                             -1,
-                             ATA_COMMAND_PROTOCOL_NONE,
-                             &input,
-                             &output,
-                             &error))
+      if (!udisks_ata_send_command_sync (fd,
+                                         -1,
+                                         UDISKS_ATA_COMMAND_PROTOCOL_NONE,
+                                         &input,
+                                         &output,
+                                         &error))
         {
           udisks_error ("Error sending ATA command SET FEATURES, sub-command 0x%02x (ata_aam_level=%d) to %s: %s (%s, %d)",
                         input.feature, data->ata_aam_level, device_file,
@@ -2137,14 +1856,14 @@ udisks_linux_drive_ata_secure_erase_sync (UDisksLinuxDriveAta     *drive,
   /* First get the IDENTIFY data directly from the drive, for sanity checks */
   {
     /* ATA8: 7.16 IDENTIFY DEVICE - ECh, PIO Data-In */
-    AtaCommandInput input = {.command = 0xec};
-    AtaCommandOutput output = {.buffer = identify.buf, .buffer_size = sizeof (identify.buf)};
-    if (!ata_send_command (fd,
-                           -1,
-                           ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST,
-                           &input,
-                           &output,
-                           &local_error))
+    UDisksAtaCommandInput input = {.command = 0xec};
+    UDisksAtaCommandOutput output = {.buffer = identify.buf, .buffer_size = sizeof (identify.buf)};
+    if (!udisks_ata_send_command_sync (fd,
+                                       -1,
+                                       UDISKS_ATA_COMMAND_PROTOCOL_DRIVE_TO_HOST,
+                                       &input,
+                                       &output,
+                                       &local_error))
       {
         g_prefix_error (&local_error, "Error sending ATA command IDENTIFY DEVICE: ");
         goto out;
@@ -2229,16 +1948,16 @@ udisks_linux_drive_ata_secure_erase_sync (UDisksLinuxDriveAta     *drive,
   {
     /* ATA8: 7.45 SECURITY SET PASSWORD - F1h, PIO Data-Out */
     guchar buf[512];
-    AtaCommandInput input = {.command = 0xf1, .buffer = buf, .buffer_size = sizeof (buf)};
-    AtaCommandOutput output = {0};
+    UDisksAtaCommandInput input = {.command = 0xf1, .buffer = buf, .buffer_size = sizeof (buf)};
+    UDisksAtaCommandOutput output = {0};
     memset (buf, 0, sizeof (buf));
     memcpy (buf + 2, pass, strlen (pass));
-    if (!ata_send_command (fd,
-                           -1,
-                           ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE,
-                           &input,
-                           &output,
-                           &local_error))
+    if (!udisks_ata_send_command_sync (fd,
+                                       -1,
+                                       UDISKS_ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE,
+                                       &input,
+                                       &output,
+                                       &local_error))
       {
         g_prefix_error (&local_error, "Error sending ATA command SECURITY SET PASSWORD: ");
         goto out;
@@ -2256,14 +1975,14 @@ udisks_linux_drive_ata_secure_erase_sync (UDisksLinuxDriveAta     *drive,
   /* Third... do SECURITY ERASE PREPARE */
   {
     /* ATA8: 7.42 SECURITY ERASE PREPARE - F3h, Non-Data */
-    AtaCommandInput input = {.command = 0xf3};
-    AtaCommandOutput output = {0};
-    if (!ata_send_command (fd,
-                           -1,
-                           ATA_COMMAND_PROTOCOL_NONE,
-                           &input,
-                           &output,
-                           &local_error))
+    UDisksAtaCommandInput input = {.command = 0xf3};
+    UDisksAtaCommandOutput output = {0};
+    if (!udisks_ata_send_command_sync (fd,
+                                       -1,
+                                       UDISKS_ATA_COMMAND_PROTOCOL_NONE,
+                                       &input,
+                                       &output,
+                                       &local_error))
       {
         g_prefix_error (&local_error, "Error sending ATA command SECURITY ERASE PREPARE: ");
         goto out;
@@ -2274,18 +1993,18 @@ udisks_linux_drive_ata_secure_erase_sync (UDisksLinuxDriveAta     *drive,
   {
     /* ATA8: 7.43 SECURITY ERASE UNIT - F4h, PIO Data-Out */
     guchar buf[512];
-    AtaCommandInput input = {.command = 0xf4, .buffer = buf, .buffer_size = sizeof (buf)};
-    AtaCommandOutput output = {0};
+    UDisksAtaCommandInput input = {.command = 0xf4, .buffer = buf, .buffer_size = sizeof (buf)};
+    UDisksAtaCommandOutput output = {0};
     memset (buf, 0, sizeof (buf));
     if (enhanced)
       buf[0] |= 0x02;
     memcpy (buf + 2, pass, strlen (pass));
-    if (!ata_send_command (fd,
-                           G_MAXINT, /* disable timeout */
-                           ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE,
-                           &input,
-                           &output,
-                           &local_error))
+    if (!udisks_ata_send_command_sync (fd,
+                                       G_MAXINT, /* disable timeout */
+                                       UDISKS_ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE,
+                                       &input,
+                                       &output,
+                                       &local_error))
       {
         g_prefix_error (&local_error, "Error sending ATA command SECURITY ERASE UNIT (enhanced=%d): ",
                         enhanced ? 1 : 0);
@@ -2305,17 +2024,17 @@ udisks_linux_drive_ata_secure_erase_sync (UDisksLinuxDriveAta     *drive,
     {
       /* ATA8: 7.41 SECURITY DISABLE PASSWORD - F6h, PIO Data-Out */
       guchar buf[512];
-      AtaCommandInput input = {.command = 0xf6, .buffer = buf, .buffer_size = sizeof (buf)};
-      AtaCommandOutput output = {0};
+      UDisksAtaCommandInput input = {.command = 0xf6, .buffer = buf, .buffer_size = sizeof (buf)};
+      UDisksAtaCommandOutput output = {0};
       GError *cleanup_error = NULL;
       memset (buf, 0, sizeof (buf));
       memcpy (buf + 2, pass, strlen (pass));
-      if (!ata_send_command (fd,
-                             -1,
-                             ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE,
-                             &input,
-                             &output,
-                             &cleanup_error))
+      if (!udisks_ata_send_command_sync (fd,
+                                         -1,
+                                         UDISKS_ATA_COMMAND_PROTOCOL_HOST_TO_DRIVE,
+                                         &input,
+                                         &output,
+                                         &cleanup_error))
         {
           udisks_error ("Failed to clear user password '%s' on %s (%s) while attemping clean-up after a failed secure erase operation. You may need to manually unlock the drive. The error was: %s (%s, %d)",
                         pass,