[haiku-commits] r40601 - haiku/trunk/src/bin

  • From: philippe.houdoin@xxxxxxxxx
  • To: haiku-commits@xxxxxxxxxxxxx
  • Date: Mon, 21 Feb 2011 19:27:38 +0100 (CET)

Author: phoudoin
Date: 2011-02-21 19:27:38 +0100 (Mon, 21 Feb 2011)
New Revision: 40601
Changeset: http://dev.haiku-os.org/changeset/40601
Ticket: http://dev.haiku-os.org/ticket/7247

Modified:
   haiku/trunk/src/bin/eject.cpp
Log:
When no device is given, find ourselves which removable device (if any) can
be considered the default one.
When several are, the command failed after listing them.
This should avoid to always fallback to floppy as
the default removable device.
Closes #7247.


Modified: haiku/trunk/src/bin/eject.cpp
===================================================================
--- haiku/trunk/src/bin/eject.cpp       2011-02-21 18:24:30 UTC (rev 40600)
+++ haiku/trunk/src/bin/eject.cpp       2011-02-21 18:27:38 UTC (rev 40601)
@@ -1,27 +1,64 @@
-// ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~
-//
-//  Copyright (c) 2003, OpenBeOS
-//
-//  This software is part of the OpenBeOS distribution and is covered
-//  by the OpenBeOS license.
-//
-//
-//  File:        eject.c
-//  Author:      François Revol (mmu_man@xxxxxxxxxxxx)
-//  Description: ejects physical media from a drive.
-//               This version also loads a media and can query for the status.
-//
-// ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~
+/*
+ * Copyright (c) 2003-2011, Haiku Inc.
+ * Distributed under the terms of the MIT license.
+ *
+ * Authors:
+ *             François Revol <mmu_man@xxxxxxxxxxxx>
+ *             Philippe Houdoin
+ *
+ * Description: ejects physical media from a drive.
+ *              This version also loads a media and can query for the status.
+ */
 
+#include <fcntl.h>
 #include <stdio.h>
-#include <fcntl.h>
 #include <string.h>
 #include <unistd.h>
+
+#include <device/scsi.h>
+#include <DiskDevice.h>
+#include <DiskDeviceRoster.h>
+#include <DiskDeviceVisitor.h>
 #include <Drivers.h>
-#include <device/scsi.h>
 #include <fs_info.h>
+#include <ObjectList.h>
+#include <Path.h>
+#include <String.h>
 
 
+class RemovableDevice {
+public:
+       RemovableDevice(BDiskDevice* device) {
+               fName = device->Name();
+               device->GetPath(&fPath);
+       };
+
+       inline const char* Name()       { return fName.String(); }
+       inline const char* Path()       { return fPath.Path(); }
+
+private:
+       BString fName;
+       BPath   fPath;
+};
+
+
+class RemovableDeviceVisitor : public BDiskDeviceVisitor {
+public:
+       virtual bool Visit(BDiskDevice* device) {
+               if (device->IsRemovableMedia())
+                       fRemovableDevices.AddItem(new RemovableDevice(device));
+               return false; // Don't stop yet!
+       }
+
+       virtual bool Visit(BPartition* partition, int32 level) { return false; }
+
+       inline BObjectList<RemovableDevice>&    RemovableDevices() { return 
fRemovableDevices; }
+
+private:
+       BObjectList<RemovableDevice>    fRemovableDevices;
+};
+
+
 static int usage(char *prog)
 {
        printf("usage: eject [-q|-l|-s|-b|-u] /dev/disk/.../raw\n");
@@ -46,7 +83,7 @@
        char operation = 'e';
        int i;
        int ret;
-       
+
        for (i = 1; i < argc; i++) {
                if (strncmp(argv[i], "--h", 3) == 0) {
                        return usage("eject");
@@ -64,8 +101,31 @@
                                return ret;
                }
        }
-       if (device == NULL)
-               return do_eject(operation, "/dev/disk/floppy/raw");
+       if (device == NULL) {
+               BDiskDeviceRoster diskDeviceRoster;
+               RemovableDeviceVisitor visitor;
+               diskDeviceRoster.VisitEachDevice(&visitor);
+
+               int32 count = visitor.RemovableDevices().CountItems();
+               if (count < 1) {
+                       printf("No removable device found!\n");
+                       return 1;
+               }
+
+               if (count > 1) {
+                       printf("Multiple removable devices available:\n");
+                       for (i = 0; i < count; i++) {
+                               RemovableDevice* item = 
visitor.RemovableDevices().ItemAt(i);
+                               printf("  %s\t\"%s\"\n", item->Path(), 
item->Name());
+                       }
+                       return 1;
+               }
+
+               // Default to single removable device found
+               device = (char*)visitor.RemovableDevices().FirstItem()->Path();
+               return do_eject(operation, device);
+       }
+
        return 0;
 }
 
@@ -77,7 +137,7 @@
        status_t devstatus;
        fs_info info;
 
-       // if the path is not on devfs, it's probably on 
+       // if the path is not on devfs, it's probably on
        // the mountpoint of the device we want to act on.
        // (should rather stat() for blk(char) device though).
        if (fs_stat_dev(dev_for_path(device), &info) >= B_OK) {


Other related posts: