[Ocfs2-tools-commits] manish commits r261 - in trunk: . ocfs2tool

svn-commits at oss.oracle.com svn-commits at oss.oracle.com
Mon Sep 27 01:00:01 CDT 2004


Author: manish
Date: 2004-09-27 00:59:59 -0500 (Mon, 27 Sep 2004)
New Revision: 261

Added:
   trunk/acinclude.m4
   trunk/ocfs2tool/
   trunk/ocfs2tool/Makefile
   trunk/ocfs2tool/bitmap.py
   trunk/ocfs2tool/browser.py
   trunk/ocfs2tool/cellmap.defs
   trunk/ocfs2tool/cellmap.override
   trunk/ocfs2tool/format.py
   trunk/ocfs2tool/general.py
   trunk/ocfs2tool/guiutil.py
   trunk/ocfs2tool/main.py
   trunk/ocfs2tool/nodemap.py
   trunk/ocfs2tool/ocfs2module.c
   trunk/ocfs2tool/ocfs2tool
   trunk/ocfs2tool/ocfs2tool.8.in
   trunk/ocfs2tool/ocfsbitmap.c
   trunk/ocfs2tool/ocfsbitmap.h
   trunk/ocfs2tool/ocfscellmap.c
   trunk/ocfs2tool/ocfscellmap.h
   trunk/ocfs2tool/ocfsmarshal.list
   trunk/ocfs2tool/ocfsplist.c
   trunk/ocfs2tool/ocfsplist.h
   trunk/ocfs2tool/process.py
Modified:
   trunk/Config.make.in
   trunk/Makefile
   trunk/autogen.sh
   trunk/configure.in
Log:
Initial landing of ocfs2tool


Modified: trunk/Config.make.in
===================================================================
--- trunk/Config.make.in	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/Config.make.in	2004-09-27 05:59:59 UTC (rev 261)
@@ -21,6 +21,7 @@
 datadir = @datadir@
 sysconfdir = @sysconfdir@
 mandir = @mandir@
+pyexecdir = @pyexecdir@
 
 top_builddir = .
 
@@ -42,10 +43,20 @@
 
 GLIB_CFLAGS = @GLIB_CFLAGS@
 GLIB_LIBS = @GLIB_LIBS@
+GLIB_GENMARSHAL = @GLIB_GENMARSHAL@
 
 GTK_CFLAGS = @GTK_CFLAGS@
 GTK_LIBS = @GTK_LIBS@
 
+PYTHON = @PYTHON@
+PYTHON_INCLUDES = @PYTHON_INCLUDES@
+
+PYGTK_CFLAGS = @PYGTK_CFLAGS@
+PYGTK_LIBS = @PYGTK_LIBS@
+
+PYGTK_CODEGEN = @PYGTK_CODEGEN@
+PYGTK_DEFSDIR = @PYGTK_DEFSDIR@
+
 BUILD_OCFSTOOL = @BUILD_OCFSTOOL@
 
 BUILD_DEBUGOCFS2 = @BUILD_DEBUGOCFS2@

Modified: trunk/Makefile
===================================================================
--- trunk/Makefile	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/Makefile	2004-09-27 05:59:59 UTC (rev 261)
@@ -29,7 +29,7 @@
 endif
 
 ifdef BUILD_OCFSTOOL
-SUBDIRS += ocfstool
+SUBDIRS += ocfs2tool
 endif
 
 SUBDIRS += vendor

Added: trunk/acinclude.m4
===================================================================
--- trunk/acinclude.m4	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/acinclude.m4	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,29 @@
+## Add your own autoconf macros here.
+
+## Find the install dirs for the python installation.
+##  By James Henstridge
+
+dnl a macro to check for ability to create python extensions
+dnl  AM_CHECK_PYTHON_HEADERS([ACTION-IF-POSSIBLE], [ACTION-IF-NOT-POSSIBLE])
+dnl function also defines PYTHON_INCLUDES
+AC_DEFUN([AM_CHECK_PYTHON_HEADERS],
+[AC_REQUIRE([AM_PATH_PYTHON])
+AC_MSG_CHECKING(for headers required to compile python extensions)
+dnl deduce PYTHON_INCLUDES
+py_prefix=`$PYTHON -c "import sys; print sys.prefix"`
+py_exec_prefix=`$PYTHON -c "import sys; print sys.exec_prefix"`
+PYTHON_INCLUDES="-I${py_prefix}/include/python${PYTHON_VERSION}"
+if test "$py_prefix" != "$py_exec_prefix"; then
+  PYTHON_INCLUDES="$PYTHON_INCLUDES -I${py_exec_prefix}/include/python${PYTHON_VERSION}"
+fi
+AC_SUBST(PYTHON_INCLUDES)
+dnl check if the headers exist:
+save_CPPFLAGS="$CPPFLAGS"
+CPPFLAGS="$CPPFLAGS $PYTHON_INCLUDES"
+AC_TRY_CPP([#include <Python.h>],dnl
+[AC_MSG_RESULT(found)
+$1],dnl
+[AC_MSG_RESULT(not found)
+$2])
+CPPFLAGS="$save_CPPFLAGS"
+])

Modified: trunk/autogen.sh
===================================================================
--- trunk/autogen.sh	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/autogen.sh	2004-09-27 05:59:59 UTC (rev 261)
@@ -1,5 +1,25 @@
 #!/bin/sh
 
-aclocal
+PROJECT=ocfs2-tools
+
+if (automake-1.9 --version) < /dev/null > /dev/null 2>&1; then
+   ACLOCAL=aclocal-1.9
+elif (automake-1.8 --version) < /dev/null > /dev/null 2>&1; then
+   ACLOCAL=aclocal-1.8
+elif (automake-1.7 --version) < /dev/null > /dev/null 2>&1; then
+   ACLOCAL=aclocal-1.7
+elif (automake-1.6 --version) < /dev/null > /dev/null 2>&1; then
+   ACLOCAL=aclocal-1.6
+else
+    echo
+    echo "  You must have automake 1.6 or newer installed to compile $PROJECT."
+    echo "  Download the appropriate package for your distribution,"
+    echo "  or get the source tarball at ftp://ftp.gnu.org/pub/gnu/automake/"
+    echo
+    exit 1
+fi
+
+rm -rf autom4te.cache
+$ACLOCAL
 autoconf
 ./configure "$@"

Modified: trunk/configure.in
===================================================================
--- trunk/configure.in	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/configure.in	2004-09-27 05:59:59 UTC (rev 261)
@@ -124,7 +124,8 @@
 AC_MSG_RESULT($enable_debugexe)
 
 GLIB_REQUIRED_VERSION=2.0.6
-GTK_REQUIRED_VERSION=2.0.6
+GTK_REQUIRED_VERSION=2.2.4
+PYGTK_REQUIRED_VERSION=1.99.16
 
 AM_PATH_GLIB_2_0($GLIB_REQUIRED_VERSION, :,
   AC_MSG_ERROR([Glib $GLIB_REQUIRED_VERSION or better is required.]))
@@ -144,17 +145,33 @@
 
 BUILD_OCFSTOOL=
 dnl AC_ARG_ENABLE(ocfstool, [  --enable-ocfstool=[yes/no]       Build GUI frontend [default=yes]],,enable_ocfstool=yes)
-dnl
-dnl if test "x$enable_ocfstool" = "xyes"; then
-dnl   AM_PATH_GTK_2_0($GTK_REQUIRED_VERSION, have_gtk=yes, have_gtk=no)
-dnl
-dnl   if test "x$have_gtk" = "xyes"; then
-dnl     BUILD_OCFSTOOL=yes
-dnl   else
-dnl     AC_MSG_WARN([GTK+ $GTK_REQUIRED_VERSION or better not found, ocfstool will not be built])
-dnl   fi
-dnl fi
+AC_ARG_ENABLE(ocfstool, [  --enable-ocfstool=[yes/no]       Build GUI frontend [default=no]],,enable_ocfstool=no)
 
+if test "x$enable_ocfstool" = "xyes"; then
+  dnl check for Python
+  AM_PATH_PYTHON(2.2)
+  AM_CHECK_PYTHON_HEADERS(,[AC_MSG_ERROR(could not find Python headers)])
+
+  dnl check for GTK
+  PKG_CHECK_MODULES(GTK, gtk+-2.0 >= $GTK_REQUIRED_VERSION)
+
+  dnl check for PyGTK
+  PKG_CHECK_MODULES(PYGTK, pygtk-2.0 >= $PYGTK_REQUIRED_VERSION)
+  AC_SUBST(PYGTK_CFLAGS)
+
+  AC_PATH_PROG(PYGTK_CODEGEN, pygtk-codegen-2.0, no)
+  if test "x$PYGTK_CODEGEN" = xno; then
+    AC_MSG_ERROR(could not find pygtk-codegen-2.0 script)
+  fi
+
+  AC_MSG_CHECKING(for pygtk defs)
+  PYGTK_DEFSDIR=`$PKG_CONFIG --variable=defsdir pygtk-2.0`
+  AC_SUBST(PYGTK_DEFSDIR)
+  AC_MSG_RESULT($PYGTK_DEFSDIR)
+
+  BUILD_OCFSTOOL=yes
+fi
+
 AC_SUBST(BUILD_OCFSTOOL)
 
 AC_OUTPUT([
@@ -162,6 +179,7 @@
 libocfs2/ocfs2_err.et
 debugfs.ocfs2/debugfs.ocfs2.8
 mkfs.ocfs2/mkfs.ocfs2.8
+ocfs2tool/ocfs2tool.8
 ocfs_uid_gen/ocfs_uid_gen.8
 load_ocfs/load_ocfs.8
 load_ocfs/ocfs.conf.5

Added: trunk/ocfs2tool/Makefile
===================================================================
--- trunk/ocfs2tool/Makefile	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/Makefile	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,70 @@
+TOPDIR = ..
+
+include $(TOPDIR)/Preamble.make
+
+WARNINGS = -Wall
+
+ifdef OCFS_DEBUG
+OPTS = -g
+endif
+OPTS = -g
+
+CFLAGS = $(OPTS) $(WARNINGS) -fPIC
+
+LIBOCFS2_CFLAGS = -I$(TOPDIR)/libocfs2/include
+LIBOCFS2_LIBS = -L$(TOPDIR)/libocfs2 -locfs2
+
+DEFINES = -DOCFS2_FLAT_INCLUDES -DG_DISABLE_DEPRECATED -DGDK_PIXBUF_DISABLE_DEPRECATED -DGDK_DISABLE_DEPRECATED -DGTK_DISABLE_DEPRECATED
+INCLUDES = $(LIBOCFS2_CFLAGS) $(PYTHON_INCLUDES) $(PYGTK_CFLAGS) $(GTK_CFLAGS)
+
+OPTIMIZE = -O2
+OPTIMIZE = -O0
+
+CFLAGS += $(OPTIMIZE)
+
+CBITS = \
+	ocfsbitmap.c \
+	ocfscellmap.c \
+	ocfsplist.c
+
+HBITS = $(subst .c,.h,$(CBITS))
+
+CFILES = $(CBITS) ocfs2module.c
+HFILES = $(HBITS)
+
+ALL = $(CFILES) ocfsmarshal.c cellmap.c
+
+OBJS = $(subst .c,.o,$(ALL))
+
+MANS = ocfs2tool.8
+
+LIBRARIES = ocfs2module.so
+
+DIST_FILES = $(CFILES) $(HFILES) ocfs2tool ocfsmarshal.list \
+	cellmap.defs cellmap.override ocfs2tool.8.in
+
+ocfsmarshal.h: ocfsmarshal.list
+	$(GLIB_GENMARSHAL) --prefix=_ocfs_marshal ocfsmarshal.list --header >> xgen-omh \
+	&& (cmp -s xgen-omh $(@F) || cp xgen-omh $(@F)) \
+	&& rm -f xgen-omh xgen-omh~
+
+ocfsmarshal.c: ocfsmarshal.list
+	echo "#include \"ocfsmarshal.h\"" >> xgen-omc \
+	&& $(GLIB_GENMARSHAL) --prefix=_ocfs_marshal ocfsmarshal.list --body >> xgen-omc \
+	&& cp xgen-omc $(@F) \
+	&& rm -f xgen-omc xgen-omc~
+
+ocfscellmap.o: ocfscellmap.c ocfsmarshal.h
+	$(CC) $(CFLAGS) $(LOCAL_CFLAGS) $(CPPFLAGS) $(LOCAL_CPPFLAGS) $(INCLUDES) $(DEFINES) -o $@ -c $<
+
+cellmap.c: cellmap.defs cellmap.override
+	$(PYGTK_CODEGEN) --prefix cellmap \
+	--register $(PYGTK_DEFSDIR)/gdk-types.defs \
+	--register $(PYGTK_DEFSDIR)/gtk-types.defs \
+	--override cellmap.override \
+	cellmap.defs > $@
+
+ocfs2module.so: $(OBJS)
+	$(LINK) -shared $(LIBOCFS2_LIBS) $(COM_ERR_LIBS) $(GTK_LIBS)
+
+include $(TOPDIR)/Postamble.make

Added: trunk/ocfs2tool/bitmap.py
===================================================================
--- trunk/ocfs2tool/bitmap.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/bitmap.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,24 @@
+import gtk
+
+import ocfs2
+
+class Bitmap:
+    def __init__(self, device=None, advanced=False):
+        self.device = device
+
+        info = self.info()
+
+        if info:
+            self.widget = gtk.ScrolledWindow()
+            self.widget.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
+            self.widget.set_border_width(4)
+            self.widget.add(info)
+        else:
+            self.widget = gtk.Label('Invalid device')
+
+    def info(self):
+        if not self.device:
+            return None
+
+        bitmap = ocfs2.Bitmap('abc', 8)
+        return ocfs2.CellMap(bitmap)

Added: trunk/ocfs2tool/browser.py
===================================================================
--- trunk/ocfs2tool/browser.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/browser.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,25 @@
+import gtk
+
+import ocfs2
+
+from guiutil import set_props
+
+class Browser:
+     def __init__(self, device=None, advanced=False):
+         self.widget = gtk.VBox(spacing=4)
+
+         scrl_win = gtk.ScrolledWindow()
+         scrl_win.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
+         self.widget.add(scrl_win)
+
+         tv = gtk.TreeView()
+         scrl_win.add(tv)
+
+         tv.insert_column_with_attributes(-1, 'File', gtk.CellRendererText(),
+                                          text=0)
+
+         table = gtk.Table(rows=4, columns=2)
+         set_props(table, row_spacing=4,
+                          column_spacing=4,
+                          border_width=4)
+         self.widget.pack_end(table)

Added: trunk/ocfs2tool/cellmap.defs
===================================================================
--- trunk/ocfs2tool/cellmap.defs	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/cellmap.defs	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,74 @@
+;; -*- scheme -*-
+; object definitions ...
+(define-object Bitmap
+  (in-module "Ocfs")
+  (parent "GObject")
+  (c-name "OcfsBitmap")
+  (gtype-id "OCFS_TYPE_BITMAP")
+)
+
+(define-object CellMap
+  (in-module "Ocfs")
+  (parent "GtkDrawingArea")
+  (c-name "OcfsCellMap")
+  (gtype-id "OCFS_TYPE_CELL_MAP")
+)
+
+;; Enumerations and flags ...
+
+
+;; From ocfsbitmap.h
+
+(define-function ocfs_bitmap_get_type
+  (c-name "ocfs_bitmap_get_type")
+  (return-type "GType")
+)
+
+(define-function ocfs_bitmap_new
+  (c-name "ocfs_bitmap_new")
+  (is-constructor-of "OcfsBitmap")
+  (return-type "OcfsBitmap*")
+  (parameters
+    '("guchar*" "data")
+    '("guint" "len")
+  )
+)
+
+
+
+;; From ocfscellmap.h
+
+(define-function ocfs_cell_map_get_type
+  (c-name "ocfs_cell_map_get_type")
+  (return-type "GType")
+)
+
+(define-function ocfs_cell_map_new
+  (c-name "ocfs_cell_map_new")
+  (is-constructor-of "OcfsCellMap")
+  (return-type "GtkWidget*")
+  (parameters
+    '("OcfsBitmap*" "map")
+  )
+)
+
+(define-method set_map
+  (of-object "OcfsCellMap")
+  (c-name "ocfs_cell_map_set_map")
+  (return-type "none")
+  (parameters
+    '("OcfsBitmap*" "map")
+  )
+)
+
+(define-method set_cell_props
+  (of-object "OcfsCellMap")
+  (c-name "ocfs_cell_map_set_cell_props")
+  (return-type "none")
+  (parameters
+    '("gint" "cell_width")
+    '("gint" "cell_height")
+  )
+)
+
+

Added: trunk/ocfs2tool/cellmap.override
===================================================================
--- trunk/ocfs2tool/cellmap.override	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/cellmap.override	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,16 @@
+%%
+headers
+#include <Python.h>               
+
+#define NO_IMPORT_PYGOBJECT
+#include "pygobject.h"
+#include "ocfscellmap.h"
+%%
+modulename ocfs2
+%%
+import gobject.GObject as PyGObject_Type
+import gtk.DrawingArea as PyGtkDrawingArea_Type
+%%
+ignore-glob
+  *_get_type                            
+%%

Added: trunk/ocfs2tool/format.py
===================================================================
--- trunk/ocfs2tool/format.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/format.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,186 @@
+import gtk
+
+import ocfs2
+
+from guiutil import set_props, error_box, format_bytes
+from process import Process
+
+class BaseCombo(gtk.Combo):
+    def __init__(self):
+        gtk.Combo.__init__(self)
+        self.entry.set_editable(False)
+
+class ValueCombo(BaseCombo):
+    def __init__(self, minimum, maximum):
+        BaseCombo.__init__(self)
+
+        choices = ['Auto']
+
+        size = minimum
+        while size <= maximum:
+            choices.append(format_bytes(size))
+            size = size << 1
+
+        self.set_popdown_strings(choices)
+
+    def get_arg(self):
+        text = self.entry.get_text()
+
+        if text != 'Auto':
+            s = text.replace(' ', '')
+            s = s.replace('B', '')
+            s = s.replace('bytes', '')
+            return (self.arg, s)
+        else:
+            return None
+
+class NumNodes(gtk.SpinButton):
+    def __init__(self):
+        adjustment = gtk.Adjustment(4, 2, ocfs2.MAX_NODES, 1, 10)
+        gtk.SpinButton.__init__(self, adjustment=adjustment, )
+
+    def get_arg(self):
+        s = self.get_text()
+
+        if s:
+            return ('-n', s)
+        else:
+            return None
+
+class Device(BaseCombo):
+    def fill(self, partitions, device):
+        for partition in partitions:
+            item = gtk.ListItem(partition)
+            item.show()
+            self.list.add(item)
+
+            if partition == device:
+                item.select()
+
+    def get_device(self):
+        return self.entry.get_text()
+
+class VolumeLabel(gtk.Entry):
+    def __init__(self):
+        gtk.Entry.__init__(self, max=ocfs2.MAX_VOL_LABEL_LEN)
+        self.set_text('oracle')
+
+    def get_arg(self):
+        s = self.get_text()
+
+        if s:
+            return ('-L', s)
+        else:
+            return None
+
+class ClusterSize(ValueCombo):
+    def __init__(self):
+        ValueCombo.__init__(self, ocfs2.MIN_CLUSTER_SIZE,
+                                  ocfs2.MAX_CLUSTER_SIZE)
+        self.arg = '-c'
+
+class BlockSize(ValueCombo):
+    def __init__(self):
+        ValueCombo.__init__(self, ocfs2.MIN_BLOCKSIZE,
+                                  ocfs2.MAX_BLOCKSIZE)
+        self.arg = '-b'
+
+entries = (
+    ('Device', Device, False),
+    ('Volume Label', VolumeLabel, False),
+    ('Cluster Size', ClusterSize, False),
+    ('Number of Nodes', NumNodes, False),
+    ('Block Size', BlockSize, True)
+)
+
+def format_partition(parent, device, advanced):
+    partitions = ocfs2.partition_list(True)
+
+    if not partitions:
+        error_box(parent, 'No unmounted partitions')
+        return False
+
+    if advanced:
+        rows = 5
+    else:
+        rows = 4
+
+    dialog = gtk.Dialog(parent=parent, title='Format',
+                        buttons=(gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL,
+                                 gtk.STOCK_OK,     gtk.RESPONSE_OK))
+
+    table = gtk.Table(rows=rows, columns=2)
+    set_props(table, row_spacing=4,
+                     column_spacing=4,
+                     border_width=4,
+                     parent=dialog.vbox)
+
+    partitions.sort()
+
+    widgets = []
+    row = 0
+
+    for desc, widget_type, advanced_only in entries:
+        if advanced_only and not advanced:
+            continue
+
+        label = gtk.Label(desc + ':')
+        set_props(label, xalign=1.0)
+        table.attach(label, 0, 1, row, row + 1)
+
+        widget = widget_type()
+        table.attach(widget, 1, 2, row, row + 1)
+
+        if widget_type == Device:
+            widget.fill(partitions, device)
+
+        widgets.append(widget)
+
+        row = row + 1
+
+    widgets[0].grab_focus()
+
+    dialog.show_all()
+ 
+    if dialog.run() != gtk.RESPONSE_OK:
+        dialog.destroy()
+        return False
+
+    dev = widgets[0].get_device()
+    msg = 'Are you sure you want to format %s?' % dev
+
+    ask = gtk.MessageDialog(parent=dialog,
+                            flags=gtk.DIALOG_DESTROY_WITH_PARENT,
+                            type=gtk.MESSAGE_QUESTION,
+                            buttons=gtk.BUTTONS_YES_NO,
+                            message_format=msg)
+
+    if ask.run() != gtk.RESPONSE_YES:
+        dialog.destroy()
+        return False
+
+    command = ['mkfs.ocfs2']
+    for widget in widgets[1:]:
+        arg = widget.get_arg()
+
+        if arg:
+            command.extend(arg)
+
+    command.append(dev)
+
+    dialog.destroy()
+
+    mkfs = Process(command, 'Format', 'Formatting...', parent)
+    success, output, k = mkfs.reap()
+
+    if not success:
+        error_box(parent, 'Format error: %s' % output)
+        return False
+
+    return True
+
+def main():
+    format(None, None, True)
+
+if __name__ == '__main__':
+    main()

Added: trunk/ocfs2tool/general.py
===================================================================
--- trunk/ocfs2tool/general.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/general.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,74 @@
+import gtk
+
+import ocfs2
+
+from guiutil import set_props, format_bytes
+
+fields = (
+    ('Version', 'version'),
+    ('Label', 's_label'),
+    ('UUID', 's_uuid'),
+    ('Maximum Nodes', 's_max_nodes'),
+    ('Cluster Size', 's_clustersize_bits'),
+    ('Block Size', 's_blocksize_bits')
+)
+
+class General:
+    def __init__(self, device=None, advanced=False):
+        self.widget = gtk.Table(rows=5, columns=2)
+
+        set_props(self.widget, row_spacing=4,
+                               column_spacing=4,
+                               border_width=4)
+
+        super = None
+
+        if device:
+            try:
+                super = ocfs2.get_super(device)
+            except ocfs2.error:
+                pass
+
+        self.pos = 0
+
+        for desc, member in fields:
+            if super:
+                if member == 'version':
+                    val = '%d.%d' % super[0:2]
+                else:
+                    val = getattr(super, member)
+
+                    if member.endswith('_bits'):
+                        val = format_bytes(1 << val)
+            else:
+                val = 'N/A'
+
+            self.add_field(desc, val)
+        
+    def add_field(self, desc, val):
+        label = gtk.Label(desc + ':')
+        set_props(label, xalign=1.0)
+        self.widget.attach(label, 0, 1, self.pos, self.pos + 1,
+                           xoptions=gtk.FILL, yoptions=gtk.FILL)
+
+        label = gtk.Label(str(val))
+        set_props(label, xalign=0.0)
+        self.widget.attach(label, 1, 2, self.pos, self.pos + 1,
+                           xoptions=gtk.FILL, yoptions=gtk.FILL)
+
+        self.pos += 1
+
+def main():
+    import sys
+
+    window = gtk.Window()
+
+    general = General(sys.argv[1], False).widget
+    window.add(general)
+
+    window.show_all()
+
+    gtk.main()
+
+if __name__ == '__main__':
+    main()

Added: trunk/ocfs2tool/guiutil.py
===================================================================
--- trunk/ocfs2tool/guiutil.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/guiutil.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,63 @@
+import gtk
+
+def set_props(obj, **kwargs):
+    for k, v in kwargs.items():
+        obj.set_property(k, v)
+
+suffixes = ['K', 'MB', 'GB', 'TB']
+
+def format_bytes(bytes, show_bytes=False):
+    if bytes == 1:
+        return '1 byte'
+    elif bytes < 1024:
+        return str(bytes) + ' bytes'
+
+    fbytes = float(bytes)
+
+    i = -1
+    while i < 3 and fbytes >= 1024:
+       fbytes /= 1024
+       i += 1
+
+    if show_bytes:
+        return '%.1f %s (%sb)' % (fbytes, suffixes[i], bytes)
+    else:
+        return '%.0f %s' % (fbytes, suffixes[i])
+
+def error_box(parent, msg):
+    dialog = gtk.MessageDialog(parent=parent,
+                               flags=gtk.DIALOG_DESTROY_WITH_PARENT,
+                               type=gtk.MESSAGE_ERROR,
+                               buttons=gtk.BUTTONS_OK, message_format=msg)
+    dialog.run()
+    dialog.destroy()
+
+def query_text(parent, prompt):
+    dialog = gtk.Dialog(parent=parent,
+                        flags=gtk.DIALOG_DESTROY_WITH_PARENT,
+                        buttons=(gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL,
+                                 gtk.STOCK_OK,     gtk.RESPONSE_OK))
+
+    table = gtk.Table(rows=1, columns=2)
+    set_props(table, row_spacing=4,
+                     column_spacing=4,
+                     border_width=4,
+                     parent=dialog.vbox)
+
+    label = gtk.Label(prompt + ':')
+    set_props(label, xalign=1.0)
+    table.attach(label, 0, 1, 0, 1)
+
+    entry = gtk.Entry()
+    table.attach(entry, 1, 2, 0, 1)
+
+    dialog.show_all()
+
+    if dialog.run() == gtk.RESPONSE_OK:
+        text = entry.get_text()
+    else:
+        text = None
+
+    dialog.destroy()
+
+    return text    

Added: trunk/ocfs2tool/main.py
===================================================================
--- trunk/ocfs2tool/main.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/main.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,337 @@
+#!/usr/bin/python
+
+import sys
+
+import gtk
+
+import ocfs2
+
+from guiutil import set_props, error_box, query_text
+from process import Process
+from format import format_partition
+from general import General
+from nodemap import NodeMap
+from bitmap import Bitmap
+from browser import Browser
+
+OCFS2TOOL_VERSION = '0.0.1'
+
+COLUMN_DEVICE = 0
+COLUMN_MOUNTPOINT = 1
+COLUMN_TYPE = 2
+
+MODE_BASIC = 0
+MODE_ADVANCED = 1
+
+notebook_items = (
+    ('general', 'General',          General),
+    ('browser', 'File Listing',     Browser),
+    ('nodemap', 'Configured Nodes', NodeMap),
+    ('bitmap',  'Bitmap View',      Bitmap),
+)
+
+def cleanup(*args):
+    gtk.main_quit()
+
+def usage(name):
+    print '''Usage: %s [OPTION]...
+Options:
+  -V, --version  print version information and exit
+      --help     display this help and exit''' % name
+
+class PartitionView(gtk.TreeView):
+    def __init__(self, toplevel):
+        store = gtk.ListStore(str, str, str)
+
+        gtk.TreeView.__init__(self, store)
+
+        self.toplevel = toplevel
+        self.advanced = MODE_BASIC
+
+        self.insert_column_with_attributes(-1, 'Device',
+                                           gtk.CellRendererText(),
+                                           text=COLUMN_DEVICE)
+        self.insert_column_with_attributes(-1, 'Type',
+                                           gtk.CellRendererText(),
+                                           text=COLUMN_TYPE)
+        self.insert_column_with_attributes(-1, 'Mountpoint',
+                                           gtk.CellRendererText(),
+                                           text=COLUMN_MOUNTPOINT)
+
+        sel = self.get_selection()
+        sel.connect('changed', self.on_select)
+
+    def get_sel_values(self):
+        sel = self.get_selection()
+        store, iter = sel.get_selected()
+
+        if store and iter:
+            return store[iter]
+        else:
+            return None
+
+    def get_device(self):
+        selection = self.get_sel_values()
+
+        if selection:
+            return selection[COLUMN_DEVICE]
+        else:
+            return None
+
+    def on_select(self, sel):
+        device, mountpoint, type = self.get_sel_values()
+
+        if mountpoint:
+            self.mount_button.set_sensitive(False)
+            self.unmount_button.set_sensitive(True)
+        else:
+            self.mount_button.set_sensitive(True)
+            self.unmount_button.set_sensitive(False)
+
+        update_notebook(self, device)
+
+    def select_device(self, device):
+        for row in self.get_model():
+            if row[COLUMN_DEVICE] == device:
+               sel = self.get_selection()
+               sel.select_iter(row.iter)
+                
+    def refresh_partitions(self):
+        def list_compare(store, a, b):
+            d1, m1, t1 = store[a]
+            d2, m2, t1 = store[b]
+
+            if m1 and not m2:
+                return -1
+            elif not m1 and m2:
+                return 1
+            else:
+                return cmp(d1, d2)
+
+        self.mount_button.set_sensitive(False)
+        self.unmount_button.set_sensitive(False)
+
+        old_device = self.get_device()
+
+        store = gtk.ListStore(str, str, str)
+        self.set_model(store)
+
+        sel = self.get_selection()
+        selected = False
+
+        for partition in ocfs2.partition_list():
+            iter = store.append(partition)
+
+            if partition[0] == old_device:
+                sel.select_iter(iter)
+                selected = True
+
+        store.set_sort_func(COLUMN_DEVICE, list_compare)
+        store.set_sort_column_id(COLUMN_DEVICE, gtk.SORT_ASCENDING)
+
+        if len(store) and not selected:
+            sel.select_iter(store.get_iter_first())
+
+def mount(button, pv):
+    device, mountpoint, type = pv.get_sel_values()
+
+    mountpoint = query_text(pv.toplevel, 'Mountpoint')
+    if not mountpoint:
+        return
+
+    command = ('mount', '-t', type, device, mountpoint)
+
+    p = Process(command, 'Mount', 'Mounting...', pv.toplevel, spin_now=False)
+    success, output, killed = p.reap()
+
+    if not success:
+        if killed:
+            error_box(pv.toplevel,
+                      'mount died unexpectedly! Your system is probably in '
+                      'an inconsistent state. You should reboot at the '
+                      'earliest opportunity')
+        else:
+            error_box(pv.toplevel, '%s: Could not mount %s' % (output, device))
+
+    pv.refresh_partitions()
+
+def unmount(button, pv):
+    device, mountpoint, type = pv.get_sel_values()
+
+    command = ('umount', mountpoint)
+
+    p = Process(command, 'Unmount', 'Unmounting...', pv.toplevel,
+                spin_now=False)
+    success, output, killed = p.reap()
+
+    if success:
+        pv.refresh_partitions()
+    else:
+        if killed:
+            error_box(pv.toplevel,
+                      'umount died unexpectedly! Your system is probably in '
+                      'an inconsistent state. You should reboot at the '
+                      'earliest opportunity')
+        else:
+            error_box(pv.toplevel,
+                      '%s: Could not unmount %s mounted on %s' %
+                      (output, device, mountpoint))
+
+def refresh(button, pv):
+    pv.refresh_partitions()
+
+    if len(pv.get_model()) == 0:
+        update_notebook(pv, None)
+
+def update_notebook(pv, device):
+    for tag, d, info in notebook_items:
+        frame = getattr(pv, tag + '-frame')
+        frame.child.destroy()
+
+        frame.add(info(device, pv.advanced).widget)
+        frame.show_all()
+
+def create_action_area(pv):
+    vbbox = gtk.VButtonBox()
+    set_props(vbbox, layout_style=gtk.BUTTONBOX_START,
+                     spacing=5,
+                     border_width=5)
+   
+    button = gtk.Button("Mount")
+    vbbox.add(button)
+    button.connect('clicked', mount, pv)
+    pv.mount_button = button
+   
+    button = gtk.Button("Unmount")
+    vbbox.add(button)
+    button.connect('clicked', unmount, pv)
+    pv.unmount_button = button
+
+    button = gtk.Button("Refresh")
+    vbbox.add(button)
+    button.connect('clicked', refresh, pv)
+
+    return vbbox
+
+def format(pv, action, w):
+    format_partition(pv.toplevel, pv.get_device(), pv.advanced)
+    pv.refresh_partitions()
+
+def genconfig(pv, action, w):
+    pass
+
+def level(pv, action, w):
+    if pv.advanced == action:
+        return
+
+    pv.advanced = action
+
+def about(pv, a, w):
+    dialog = gtk.MessageDialog(parent=pv.toplevel,
+                               flags=gtk.DIALOG_DESTROY_WITH_PARENT,
+                               buttons=gtk.BUTTONS_CLOSE)
+    dialog.label.set_text('''OCFS2 Tool
+Version %s
+Copyright (C) Oracle Corporation 2002, 2004
+All Rights Reserved''' % OCFS2TOOL_VERSION)
+
+    dialog.run()
+    dialog.destroy()
+
+menu_items = (
+    ('/_File',                     None,         None,      0, '<Branch>'),
+    ('/File/_Quit',                None,         cleanup,   0, '<StockItem>', gtk.STOCK_QUIT),
+    ('/_Tasks',                    None,         None,      0, '<Branch>'),
+    ('/Tasks/_Format...',          '<control>F', format,    0),
+    #('/Tasks/---',                 None,         None,      0, '<Separator>'),
+    #('/Tasks/_Generate Config...', '<control>G', genconfig, 0),
+    ('/_Preferences',              None,         None,      0, '<Branch>'),
+    ('/Preferences/_Basic',        '<control>B', level,     MODE_BASIC, '<RadioItem>'),
+    ('/Preferences/_Advanced',     '<control>A', level,     MODE_ADVANCED, '/Preferences/Basic'),
+    ('/_Help',                     None,         None,      0, '<Branch>'),
+    ('/Help/_About',               None,         about,     0)
+)
+
+def create_window():
+    window = gtk.Window()
+    set_props(window, title='OCFS2 Tool',
+                      default_width=520,
+                      default_height=420,
+                      border_width=0)
+    window.connect('delete_event', cleanup)
+
+    pv = PartitionView(window)
+
+    accel_group = gtk.AccelGroup()
+    window.add_accel_group(accel_group)
+
+    item_factory = gtk.ItemFactory(gtk.MenuBar, '<main>', accel_group)
+    item_factory.create_items(menu_items, pv)
+    window.item_factory = item_factory
+
+    vbox = gtk.VBox()
+    window.add(vbox)
+
+    menubar = item_factory.get_widget('<main>')
+    vbox.pack_start(menubar, expand=False, fill=False)
+
+    vpaned = gtk.VPaned()
+    vpaned.set_border_width(4)
+    vbox.pack_start(vpaned, expand=True, fill=True)
+
+    hbox = gtk.HBox()
+    vpaned.pack1(hbox)
+
+    scrl_win = gtk.ScrolledWindow()
+    set_props(scrl_win, hscrollbar_policy=gtk.POLICY_AUTOMATIC,
+                        vscrollbar_policy=gtk.POLICY_AUTOMATIC,
+                        parent=hbox)
+
+    scrl_win.add(pv)
+
+    frame = gtk.Frame()
+    frame.set_shadow_type(gtk.SHADOW_IN)
+    hbox.pack_end(frame, expand=False, fill=False)
+
+    vbbox = create_action_area(pv)
+    frame.add(vbbox)
+
+    notebook = gtk.Notebook()
+    notebook.set_tab_pos(gtk.POS_TOP)
+    vpaned.pack2(notebook)
+
+    for tag, desc, info in notebook_items:
+        frame = gtk.Frame()
+        set_props(frame, shadow=gtk.SHADOW_NONE,
+                         border_width=0)
+
+        tag = tag + '-frame'
+        setattr(pv, tag, frame)
+
+        frame.add(info().widget)
+        frame.show_all()
+
+        notebook.add_with_properties(frame, 'tab_label', desc)
+
+    pv.refresh_partitions()
+
+    window.show_all()
+
+def main():
+    for arg in sys.argv[1:]:
+        if arg == '--version' or arg == '-V':
+            print 'OCFS2Tool version %s' % OCFS2TOOL_VERSION
+            sys.exit(0)
+        elif arg == '--help':
+            usage(sys.argv[0])
+            sys.exit(0)
+        else:
+            usage(sys.argv[0])
+            sys.exit(1)
+
+    create_window()
+
+    gtk.main()
+
+if __name__ == '__main__':
+    main()


Property changes on: trunk/ocfs2tool/main.py
___________________________________________________________________
Name: svn:executable
   + *

Added: trunk/ocfs2tool/nodemap.py
===================================================================
--- trunk/ocfs2tool/nodemap.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/nodemap.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,65 @@
+import gtk
+
+import ocfs2
+
+COLUMN_SLOT = 0
+COLUMN_NAME = 1
+COLUMN_IP = 2
+COLUMN_PORT = 3
+COLUMN_UUID = 4
+
+class NodeMap:
+    def __init__(self, device=None, advanced=False):
+        self.device = device
+        self.advanced = advanced
+
+        info = self.info()
+
+        if info:
+            self.widget = gtk.ScrolledWindow()
+            self.widget.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC)
+            self.widget.add(info)
+        else:
+            self.widget = gtk.Label('Invalid device')
+
+    def info(self):
+        if not self.device:
+            return None
+
+        store = gtk.ListStore(int, str, str, int, str)
+
+        tv = gtk.TreeView(store)
+        
+        tv.insert_column_with_attributes(-1, 'Slot #',
+                                         gtk.CellRendererText(),
+                                         text=COLUMN_SLOT)
+        tv.insert_column_with_attributes(-1, 'Node Name',
+                                         gtk.CellRendererText(),
+                                         text=COLUMN_NAME)
+        tv.insert_column_with_attributes(-1, 'IP Address',
+                                         gtk.CellRendererText(),
+                                         text=COLUMN_IP)
+        tv.insert_column_with_attributes(-1, 'Port',
+                                         gtk.CellRendererText(),
+                                         text=COLUMN_PORT)
+
+        if self.advanced:
+            tv.insert_column_with_attributes(-1, 'UUID',
+                                             gtk.CellRendererText(),
+                                             text=COLUMN_UUID)
+
+        return tv
+def main():
+    import sys
+
+    window = gtk.Window()
+    window.show()
+
+    nodemap = NodeMap(sys.argv[1], False).widget
+    window.add(nodemap)
+
+    window.show_all()
+    gtk.main()
+
+if __name__ == '__main__':
+    main()

Added: trunk/ocfs2tool/ocfs2module.c
===================================================================
--- trunk/ocfs2tool/ocfs2module.c	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/ocfs2module.c	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,248 @@
+/*
+ * ocfs2module.c
+ *
+ * OCFS2 python binding.
+ *
+ * Copyright (C) 2004 Oracle.  All rights reserved.
+ *
+ * Author: Manish Singh <manish.singh at oracle.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have recieved a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 021110-1307, USA.
+ */
+
+#include "Python.h"
+#include "structseq.h"
+
+#include <glib.h>
+
+#include <pygobject.h>
+#include <pygtk/pygtk.h>
+
+#include "ocfs2.h"
+
+#include "ocfsplist.h"
+
+
+#define MAX_CLUSTER_SIZE       1048576
+#define MIN_CLUSTER_SIZE       4096
+
+
+void cellmap_register_classes (PyObject *d);
+extern PyMethodDef cellmap_functions[];
+
+
+static PyObject *ocfs2_error;
+
+static PyObject *
+partition_list (PyObject *self,
+		PyObject *args)
+{
+  gboolean           unmounted = FALSE, bail = FALSE;
+  GList             *list, *last;
+  PyObject          *ret, *val;
+  OcfsPartitionInfo *info;
+
+  if (!PyArg_ParseTuple (args, "|i:partition_list", &unmounted))
+    return NULL;
+
+  list = ocfs_partition_list (unmounted);
+
+  ret = PyList_New (0);
+  if (ret == NULL)
+    bail = TRUE;
+
+  while (list)
+    {
+
+      if (!bail)
+	{
+	  if (!unmounted)
+	    {
+	      info = list->data;
+	      val = Py_BuildValue ("(sss)",
+				   info->device, info->mountpoint,
+				   info->type == OCFS_FS_TYPE_OCFS2 ? "ocfs2"
+								    : "ocfs");
+	    }
+	  else
+	    val = PyString_FromString (list->data);
+
+	  if (val)
+	    {
+	      PyList_Append (ret, val);
+	      Py_DECREF (val);
+	    }
+	  else
+	    bail = TRUE;
+	}
+
+      if (!unmounted)
+	{
+	  g_free (info->device);
+	  g_free (info->mountpoint);
+	  g_free (info);
+        }
+      else
+	g_free (list->data);
+
+      last = list;
+      list = list->next;
+
+      g_list_free_1 (last);
+    }
+
+  if (bail)
+    {
+      Py_XDECREF (ret);
+      return NULL;
+    }
+  else
+    return ret;
+}
+
+static PyStructSequence_Field struct_ocfs2_super_fields[] = {
+  {"s_major_rev_level",  "major revision level"},
+  {"s_minor_rev_level",  "minor revision level"},
+  {"s_blocksize_bits",   "blocksize bits"},
+  {"s_clustersize_bits", "cluster size bits"},
+  {"s_max_nodes",        "maximum nodes"},
+  {"s_label",            "volume label"},
+  {"s_uuid",             "UUID"},
+  {0}
+};
+
+struct PyStructSequence_Desc struct_ocfs2_super_desc = {
+  "ocfs2.struct_ocfs2_super",
+  NULL,
+  struct_ocfs2_super_fields,
+  7,
+};
+
+static PyTypeObject StructOcfs2SuperType;
+
+static PyObject *
+get_super (PyObject *self,
+	   PyObject *args)
+{
+  gchar         *device;
+  errcode_t      ret;
+  ocfs2_filesys *fs;
+  PyObject      *v;
+  gint           index = 0;
+  GString       *uuid;
+  gint           i;
+
+  if (!PyArg_ParseTuple (args, "s:get_super", &device))
+    return NULL;
+
+  ret = ocfs2_open (device, OCFS2_FLAG_RO, 0, 0, &fs);
+  if (ret)
+    {
+      PyErr_SetString (ocfs2_error, error_message (ret));
+      return NULL;
+    }
+
+  v = PyStructSequence_New (&StructOcfs2SuperType);
+  if (v == NULL)
+    return NULL;
+
+#define SET(m) \
+  PyStructSequence_SET_ITEM (v, index++, PyInt_FromLong \
+    (OCFS2_RAW_SB (fs->fs_super)->m));
+
+  SET (s_major_rev_level);
+  SET (s_minor_rev_level);
+  SET (s_blocksize_bits);
+  SET (s_clustersize_bits);
+  SET (s_max_nodes);
+
+#undef SET
+#define SET(m) \
+  PyStructSequence_SET_ITEM \
+    (v, index++, PyString_FromString (OCFS2_RAW_SB (fs->fs_super)->m));
+
+  PyStructSequence_SET_ITEM
+    (v, index++, PyString_FromString (OCFS2_RAW_SB (fs->fs_super)->s_label));
+
+#undef SET
+
+  uuid = g_string_sized_new (32);
+
+  for (i = 0; i < 16; i++)
+    g_string_append_printf (uuid, "%02X",
+			    OCFS2_RAW_SB (fs->fs_super)->s_uuid[i]);
+
+  PyStructSequence_SET_ITEM (v, index++, PyString_FromString (uuid->str));
+
+  g_string_free (uuid, TRUE);
+
+  ocfs2_close (fs);
+
+  if (PyErr_Occurred())
+    {
+      Py_DECREF (v);
+      return NULL;
+    }
+
+  return v;
+}
+
+static PyMethodDef ocfs2_methods[] = {
+  {"partition_list", partition_list, METH_VARARGS},
+  {"get_super", get_super, METH_VARARGS},
+  {NULL,       NULL}    /* sentinel */
+};
+
+void
+initocfs2 (void)
+{
+  PyObject *m, *d;
+
+  init_pygobject ();
+  init_pygtk ();
+
+  initialize_ocfs_error_table ();
+
+  m = Py_InitModule ("ocfs2", ocfs2_methods);
+
+  PyStructSequence_InitType (&StructOcfs2SuperType, &struct_ocfs2_super_desc);
+  Py_INCREF (&StructOcfs2SuperType);
+  PyModule_AddObject (m, "struct_ocfs2_super",
+                      (PyObject *) &StructOcfs2SuperType);
+
+  ocfs2_error = PyErr_NewException ("ocfs2.error", PyExc_RuntimeError, NULL);
+  if (ocfs2_error)
+    {
+      Py_INCREF (ocfs2_error);
+      PyModule_AddObject (m, "error", ocfs2_error);
+    }
+
+  PyModule_AddIntConstant (m, "MAX_VOL_LABEL_LEN", MAX_VOL_LABEL_LEN);
+  PyModule_AddIntConstant (m, "MAX_NODES", OCFS2_MAX_NODES);
+
+  PyModule_AddIntConstant (m, "MIN_BLOCKSIZE", OCFS2_MIN_BLOCKSIZE);
+  PyModule_AddIntConstant (m, "MAX_BLOCKSIZE", OCFS2_MAX_BLOCKSIZE);
+
+  PyModule_AddIntConstant (m, "MIN_CLUSTER_SIZE", MIN_CLUSTER_SIZE);
+  PyModule_AddIntConstant (m, "MAX_CLUSTER_SIZE", MAX_CLUSTER_SIZE);
+
+  d = PyModule_GetDict (m);
+
+  cellmap_register_classes (d);
+
+  if (PyErr_Occurred ())
+    Py_FatalError ("can't initialise module ocfs2");
+}

Added: trunk/ocfs2tool/ocfs2tool
===================================================================
--- trunk/ocfs2tool/ocfs2tool	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/ocfs2tool	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,6 @@
+#!/usr/bin/python
+
+from main import main
+
+if __name__ == '__main__':
+    main()


Property changes on: trunk/ocfs2tool/ocfs2tool
___________________________________________________________________
Name: svn:executable
   + *

Copied: trunk/ocfs2tool/ocfs2tool.8.in (from rev 259, trunk/ocfstool/ocfstool.8.in)

Added: trunk/ocfs2tool/ocfsbitmap.c
===================================================================
--- trunk/ocfs2tool/ocfsbitmap.c	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/ocfsbitmap.c	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,107 @@
+/*
+ * ocfsbitmap.c
+ *
+ * A simple object containing a bitmap
+ *
+ * Copyright (C) 2004 Oracle Corporation.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 021110-1307, USA.
+ *
+ * Author: Manish Singh
+ */
+
+#include <glib-object.h>
+
+#include "ocfsbitmap.h"
+
+
+static void     ocfs_bitmap_class_init      (OcfsBitmapClass  *class);
+static void     ocfs_bitmap_init            (OcfsBitmap       *bitmap);
+static void     ocfs_bitmap_finalize        (GObject           *object);
+
+
+static GObjectClass *parent_class = NULL;
+
+
+GType
+ocfs_bitmap_get_type (void)
+{
+  static GType bitmap_type = 0;
+
+  if (! bitmap_type)
+    {
+      static const GTypeInfo bitmap_info =
+      {
+	sizeof (OcfsBitmapClass),
+	(GBaseInitFunc) NULL,
+	(GBaseFinalizeFunc) NULL,
+	(GClassInitFunc) ocfs_bitmap_class_init,
+	NULL,           /* class_finalize */
+	NULL,           /* class_data     */
+	sizeof (OcfsBitmap),
+	0,              /* n_preallocs    */
+	(GInstanceInitFunc) ocfs_bitmap_init,
+      };
+
+      bitmap_type = g_type_register_static (G_TYPE_OBJECT, "OcfsBitmap",
+					    &bitmap_info, 0);
+    }
+  
+  return bitmap_type;
+}
+
+static void
+ocfs_bitmap_class_init (OcfsBitmapClass *class)
+{
+  GObjectClass *object_class;
+
+  object_class = (GObjectClass *) class;
+
+  parent_class = g_type_class_peek_parent (class);
+
+  object_class->finalize = ocfs_bitmap_finalize;
+}
+
+static void
+ocfs_bitmap_init (OcfsBitmap *bitmap)
+{
+  bitmap->data = NULL;
+  bitmap->len = 0;
+}
+
+static void
+ocfs_bitmap_finalize (GObject *object)
+{
+  OcfsBitmap *bitmap = OCFS_BITMAP (object);
+
+  g_free (bitmap->data);
+
+  G_OBJECT_CLASS (parent_class)->finalize (object);
+}
+
+OcfsBitmap *
+ocfs_bitmap_new (guchar *data,
+                 guint   len)
+{
+  OcfsBitmap *bitmap;
+
+  bitmap = g_object_new (OCFS_TYPE_BITMAP, NULL);
+
+  bitmap->data = data;
+  bitmap->len  = len;
+
+  return bitmap;
+}

Added: trunk/ocfs2tool/ocfsbitmap.h
===================================================================
--- trunk/ocfs2tool/ocfsbitmap.h	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/ocfsbitmap.h	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,63 @@
+/*
+ * ocfsbitmap.h
+ *
+ * Function prototypes for related 'C' file.
+ *
+ * Copyright (C) 2004 Oracle Corporation.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 021110-1307, USA.
+ *
+ * Author: Manish Singh
+ */
+
+#ifndef __OCFS_BITMAP_H__
+#define __OCFS_BITMAP_H__
+
+
+#include <glib-object.h>
+
+
+#define OCFS_TYPE_BITMAP            (ocfs_bitmap_get_type ())
+#define OCFS_BITMAP(obj)            (G_TYPE_CHECK_INSTANCE_CAST ((obj), OCFS_TYPE_BITMAP, OcfsBitmap))
+#define OCFS_BITMAP_CLASS(klass)    (G_TYPE_CHECK_CLASS_CAST ((klass), OCFS_TYPE_BITMAP, OcfsBitmapClass))
+#define OCFS_IS_BITMAP(obj)         (G_TYPE_CHECK_INSTANCE_TYPE ((obj), OCFS_TYPE_BITMAP))
+#define OCFS_IS_BITMAP_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), OCFS_TYPE_BITMAP))
+#define OCFS_BITMAP_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), OCFS_TYPE_BITMAP, OcfsBitmapCLass))
+
+
+typedef struct _OcfsBitmap      OcfsBitmap;
+typedef struct _OcfsBitmapClass OcfsBitmapClass;
+
+struct _OcfsBitmap
+{
+  GObject  parent_instance;
+
+  guchar  *data;
+  guint    len;
+};
+
+struct _OcfsBitmapClass
+{
+  GObjectClass parent_class;
+};
+
+
+GType       ocfs_bitmap_get_type (void);
+OcfsBitmap *ocfs_bitmap_new      (guchar *data,
+                                  guint   len);
+
+
+#endif /* __OCFS_BITMAP_H__ */

Copied: trunk/ocfs2tool/ocfscellmap.c (from rev 256, trunk/ocfstool/ocfscellmap.c)
===================================================================
--- trunk/ocfstool/ocfscellmap.c	2004-09-24 23:55:36 UTC (rev 256)
+++ trunk/ocfs2tool/ocfscellmap.c	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,646 @@
+/*
+ * ocfscellmap.c
+ *
+ * A scrollable bitmap display widget
+ *
+ * Copyright (C) 2002 Oracle Corporation.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 021110-1307, USA.
+ *
+ * Author: Manish Singh
+ */
+
+#include <gtk/gtk.h>
+
+#include "ocfscellmap.h"
+
+#include "ocfsmarshal.h"
+
+
+#define DEFAULT_CELL_WIDTH  10
+#define DEFAULT_CELL_HEIGHT 10
+
+#define CELL_MAP_MASK       (GDK_EXPOSURE_MASK |            \
+			     GDK_POINTER_MOTION_MASK |      \
+			     GDK_POINTER_MOTION_HINT_MASK | \
+			     GDK_ENTER_NOTIFY_MASK |        \
+			     GDK_BUTTON_PRESS_MASK |        \
+			     GDK_BUTTON_RELEASE_MASK |      \
+			     GDK_BUTTON1_MOTION_MASK)
+
+
+enum {
+  PROP_0,
+  PROP_MAP,
+  PROP_CELL_WIDTH,
+  PROP_CELL_HEIGHT,
+  PROP_HADJUSTMENT,
+  PROP_VADJUSTMENT
+};
+
+
+static void     ocfs_cell_map_class_init      (OcfsCellMapClass  *class);
+static void     ocfs_cell_map_init            (OcfsCellMap       *cell_map);
+static void     ocfs_cell_map_set_property    (GObject           *object,
+					       guint              property_id,
+					       const GValue      *value,
+					       GParamSpec        *pspec);
+static void     ocfs_cell_map_get_property    (GObject           *object,
+					       guint              property_id,
+					       GValue            *value,
+					       GParamSpec        *pspec);
+static void     ocfs_cell_map_finalize        (GObject           *object);
+static void     ocfs_cell_map_size_request    (GtkWidget         *widget,
+					       GtkRequisition    *requisition);
+static void     paint_cell_map                (GtkWidget         *widget);
+static void     ocfs_cell_map_state_changed   (GtkWidget         *widget,
+					       GtkStateType       old_state);
+static gboolean ocfs_cell_map_configure       (GtkWidget         *widget,
+					       GdkEventConfigure *event);
+static gboolean ocfs_cell_map_expose          (GtkWidget         *widget,
+					       GdkEventExpose    *event);
+static gboolean ocfs_cell_map_button_press    (GtkWidget         *widget,
+					       GdkEventButton    *event);
+static gboolean ocfs_cell_map_button_release  (GtkWidget         *widget,
+					       GdkEventButton    *event);
+static gboolean ocfs_cell_map_motion_notify   (GtkWidget         *widget,
+					       GdkEventMotion    *event);
+static void     ocfs_cell_map_set_adjustments (OcfsCellMap       *cell_map,
+					       GtkAdjustment     *hadj,
+					       GtkAdjustment     *vadj);
+static void     update_adjustment             (GtkAdjustment     *adj,
+					       OcfsCellMap       *cell_map);
+static void     compute_vertical_scroll       (OcfsCellMap       *cell_map);
+
+
+static GtkDrawingAreaClass *parent_class = NULL;
+
+
+GType
+ocfs_cell_map_get_type (void)
+{
+  static GType cell_map_type = 0;
+
+  if (! cell_map_type)
+    {
+      static const GTypeInfo cell_map_info =
+      {
+	sizeof (OcfsCellMapClass),
+	(GBaseInitFunc) NULL,
+	(GBaseFinalizeFunc) NULL,
+	(GClassInitFunc) ocfs_cell_map_class_init,
+	NULL,           /* class_finalize */
+	NULL,           /* class_data     */
+	sizeof (OcfsCellMap),
+	0,              /* n_preallocs    */
+	(GInstanceInitFunc) ocfs_cell_map_init,
+      };
+
+      cell_map_type = g_type_register_static (GTK_TYPE_DRAWING_AREA,
+					      "OcfsCellMap",
+					      &cell_map_info, 0);
+    }
+  
+  return cell_map_type;
+}
+
+static void
+ocfs_cell_map_class_init (OcfsCellMapClass *class)
+{
+  GObjectClass   *object_class;
+  GtkWidgetClass *widget_class;
+
+  object_class = (GObjectClass *) class;
+  widget_class = (GtkWidgetClass *) class;
+
+  parent_class = g_type_class_peek_parent (class);
+
+  object_class->set_property = ocfs_cell_map_set_property;
+  object_class->get_property = ocfs_cell_map_get_property;
+  object_class->finalize = ocfs_cell_map_finalize;
+
+  g_object_class_install_property (object_class,
+				   PROP_MAP,
+				   g_param_spec_object ("map",
+							"Map",
+							"The cell bitmap",
+							OCFS_TYPE_BITMAP,
+							G_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class,
+				   PROP_CELL_WIDTH,
+				   g_param_spec_int ("cell_width",
+						     "Cell Width",
+						     "The width of each cell in pixels",
+						     -1,
+						     G_MAXINT,
+						     DEFAULT_CELL_WIDTH,
+						     G_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class,
+				   PROP_CELL_HEIGHT,
+				   g_param_spec_int ("cell_height",
+						     "Cell Height",
+						     "The height of each cell in pixels",
+						     -1,
+						     G_MAXINT,
+						     DEFAULT_CELL_HEIGHT,
+						     G_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class,
+				   PROP_HADJUSTMENT,
+				   g_param_spec_object ("hadjustment",
+							"Horizontal Adjustment",
+							"The GtkAdjustment for the horizontal position",
+							GTK_TYPE_ADJUSTMENT,
+							G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+  g_object_class_install_property (object_class,
+				   PROP_VADJUSTMENT,
+				   g_param_spec_object ("vadjustment",
+							"Vertical Adjustment",
+							"The GtkAdjustment for the vertical position",
+							GTK_TYPE_ADJUSTMENT,
+							G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
+
+  widget_class->state_changed = ocfs_cell_map_state_changed;
+  widget_class->size_request = ocfs_cell_map_size_request;
+  widget_class->configure_event = ocfs_cell_map_configure;
+  widget_class->expose_event = ocfs_cell_map_expose;
+
+  widget_class->button_press_event = ocfs_cell_map_button_press;
+  widget_class->button_release_event = ocfs_cell_map_button_release;
+  widget_class->motion_notify_event = ocfs_cell_map_motion_notify;
+
+  widget_class->set_scroll_adjustments_signal =
+    g_signal_new ("set_scroll_adjustments",
+		  G_OBJECT_CLASS_TYPE (object_class),
+		  G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
+		  G_STRUCT_OFFSET (OcfsCellMapClass, set_scroll_adjustments),
+		  NULL, NULL,
+		  _ocfs_marshal_VOID__OBJECT_OBJECT,
+		  G_TYPE_NONE, 2,
+		  GTK_TYPE_ADJUSTMENT,
+		  GTK_TYPE_ADJUSTMENT);
+
+  class->set_scroll_adjustments = ocfs_cell_map_set_adjustments;
+}
+
+static void
+ocfs_cell_map_init (OcfsCellMap *cell_map)
+{
+  gint old_mask;
+
+  cell_map->map = NULL;
+
+  cell_map->cell_width = DEFAULT_CELL_WIDTH;
+  cell_map->cell_height = DEFAULT_CELL_HEIGHT;
+
+  cell_map->hadj = NULL;
+  cell_map->vadj = NULL;
+
+  old_mask = gtk_widget_get_events (GTK_WIDGET (cell_map));
+  gtk_widget_set_events (GTK_WIDGET (cell_map), old_mask | CELL_MAP_MASK);
+}
+
+static void
+ocfs_cell_map_set_property (GObject      *object,
+			    guint         property_id,
+			    const GValue *value,
+			    GParamSpec   *pspec)
+{
+  OcfsCellMap *cell_map = OCFS_CELL_MAP (object);
+
+  switch (property_id)
+    {
+    case PROP_MAP:
+      ocfs_cell_map_set_map (cell_map, g_value_get_object (value));
+      break;
+    case PROP_CELL_WIDTH:
+      cell_map->cell_width = g_value_get_int (value);
+      break;
+    case PROP_CELL_HEIGHT:
+      cell_map->cell_height = g_value_get_int (value);
+      break;
+    case PROP_HADJUSTMENT:
+      ocfs_cell_map_set_adjustments (cell_map, g_value_get_object (value),
+				     cell_map->vadj);
+      break;
+    case PROP_VADJUSTMENT:
+      ocfs_cell_map_set_adjustments (cell_map, cell_map->hadj,
+				     g_value_get_object (value));
+      break;
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
+      break;
+    }
+}
+
+static void
+ocfs_cell_map_get_property (GObject *object,
+			    guint       property_id,
+                            GValue     *value,
+			    GParamSpec *pspec)
+
+{
+  OcfsCellMap *cell_map = OCFS_CELL_MAP (object);
+
+  switch (property_id)
+    {
+    case PROP_MAP:
+      g_value_set_object (value, cell_map->map);
+      break;
+    case PROP_CELL_WIDTH:
+      g_value_set_int (value, cell_map->cell_width);
+      break;
+    case PROP_CELL_HEIGHT:
+      g_value_set_int (value, cell_map->cell_height);
+      break;
+    case PROP_HADJUSTMENT:
+      g_value_set_object (value, cell_map->hadj);
+      break;
+    case PROP_VADJUSTMENT:
+      g_value_set_object (value, cell_map->vadj);
+      break;
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
+      break;
+    }
+}
+
+static void
+ocfs_cell_map_finalize (GObject *object)
+{
+  OcfsCellMap *cell_map = OCFS_CELL_MAP (object);
+
+  g_object_unref (cell_map->hadj);
+  g_object_unref (cell_map->vadj);
+ 
+  if (cell_map->map)
+    g_object_unref (cell_map->map);
+
+  G_OBJECT_CLASS (parent_class)->finalize (object);
+}
+
+GtkWidget *
+ocfs_cell_map_new (OcfsBitmap *map)
+{
+  return g_object_new (OCFS_TYPE_CELL_MAP,
+		       "map", map,
+		       NULL);
+}
+
+void
+ocfs_cell_map_set_map (OcfsCellMap *cell_map,
+		       OcfsBitmap  *map)
+{
+  g_return_if_fail (OCFS_IS_CELL_MAP (cell_map));
+
+  if (cell_map->map)
+    g_object_unref (cell_map->map);
+
+  cell_map->map = g_object_ref (map);
+  g_object_notify (G_OBJECT (cell_map), "map");
+
+  gtk_widget_queue_draw (GTK_WIDGET (cell_map));
+}
+
+void
+ocfs_cell_map_set_cell_props (OcfsCellMap *cell_map,
+			      gint         cell_width,
+			      gint         cell_height)
+{
+  g_return_if_fail (OCFS_IS_CELL_MAP (cell_map));
+  
+#define SET_PROP(prop, def)	G_STMT_START {	\
+  if (prop > -1)				\
+    cell_map->prop = prop;			\
+  else if (prop == -1)				\
+    cell_map->prop = def;	} G_STMT_END
+
+  SET_PROP (cell_width, DEFAULT_CELL_WIDTH);
+  SET_PROP (cell_height, DEFAULT_CELL_HEIGHT);
+
+#undef SET_PROP
+
+  compute_vertical_scroll (cell_map);
+}
+
+static void
+ocfs_cell_map_state_changed (GtkWidget    *widget,
+			     GtkStateType  old_state)
+{
+  gtk_widget_queue_draw (widget);
+}
+
+static void
+ocfs_cell_map_size_request (GtkWidget      *widget,
+			    GtkRequisition *requisition)
+{
+  OcfsCellMap *cell_map = OCFS_CELL_MAP (widget);
+
+  requisition->width  = cell_map->cell_width;
+  requisition->height = cell_map->cell_height;
+}
+
+static void
+paint_cell_map (GtkWidget *widget)
+{
+  OcfsCellMap  *cell_map = OCFS_CELL_MAP (widget);
+  GtkStateType  state, type;
+  gint          i;
+  gint          width, height;
+  gint          dx, dy;
+  gint          per_row;
+  gint          start, end;
+  gint          val;
+
+  gtk_paint_flat_box (widget->style,
+		      widget->window,
+		      GTK_STATE_NORMAL, GTK_SHADOW_NONE,
+		      NULL, widget, "cell_map_bg",
+		      0, 0,
+		      widget->allocation.width,
+		      widget->allocation.height);
+
+  if (cell_map && cell_map->map->len)
+    {
+      width  = widget->allocation.width  - 1;
+      height = widget->allocation.height - 1;
+
+      per_row = width / cell_map->cell_width;
+      per_row = MAX (1, per_row);
+      
+      val = cell_map->vadj->value;
+
+      start = val / cell_map->cell_height * per_row;
+      end = height / cell_map->cell_height * per_row + start;
+      end = MIN (end, cell_map->map->len);
+
+      if (end != cell_map->map->len && end + per_row > cell_map->map->len)
+	{
+	  if (val % cell_map->cell_height)
+	    {
+	      start += per_row;
+	      end = cell_map->map->len;
+	    }
+	}
+
+      state = GTK_STATE_NORMAL;
+      if (!GTK_WIDGET_IS_SENSITIVE (widget))
+	state = GTK_STATE_INSENSITIVE;
+
+      for (i = start; i < end; i++)
+	{
+	  dx = (i % per_row) * cell_map->cell_width;
+	  dy = ((i - start) / per_row) * cell_map->cell_height;
+
+	  type = cell_map->map->data[i] ? GTK_STATE_SELECTED
+					: state;
+
+	  gdk_draw_rectangle (widget->window,
+			      widget->style->fg_gc[state],
+			      FALSE,
+			      dx, dy,
+			      cell_map->cell_width,
+			      cell_map->cell_height);
+
+	  gdk_draw_rectangle (widget->window,
+			      widget->style->bg_gc[type],
+			      TRUE,
+			      dx + 1, dy + 1,
+			      cell_map->cell_width - 1,
+			      cell_map->cell_height - 1);
+	}
+    }
+}
+
+static gboolean
+ocfs_cell_map_configure (GtkWidget         *widget,
+			 GdkEventConfigure *event)
+{
+  OcfsCellMap *cell_map = OCFS_CELL_MAP (widget);
+
+  compute_vertical_scroll (cell_map);
+
+  return FALSE;
+}
+
+static gboolean
+ocfs_cell_map_expose (GtkWidget      *widget,
+		      GdkEventExpose *event)
+{
+  if (GTK_WIDGET_DRAWABLE (widget))
+    paint_cell_map (widget);
+
+  return FALSE;
+}
+
+static gboolean
+ocfs_cell_map_button_press (GtkWidget      *widget,
+			    GdkEventButton *event)
+{
+  return FALSE;
+}
+
+static gboolean
+ocfs_cell_map_button_release (GtkWidget      *widget,
+			      GdkEventButton *event)
+{
+  return FALSE;
+}
+
+static gboolean
+ocfs_cell_map_motion_notify (GtkWidget      *widget,
+			     GdkEventMotion *event)
+{
+  return FALSE;
+}
+
+static void
+ocfs_cell_map_set_adjustments (OcfsCellMap   *cell_map,
+			       GtkAdjustment *hadj,
+			       GtkAdjustment *vadj)
+{
+  if (hadj)
+    g_return_if_fail (GTK_IS_ADJUSTMENT (hadj));
+  else
+    hadj = GTK_ADJUSTMENT (gtk_adjustment_new (0.0, 0.0, 0.0, 0.0, 0.0, 0.0));
+
+  if (vadj)
+    g_return_if_fail (GTK_IS_ADJUSTMENT (vadj));
+  else
+    vadj = GTK_ADJUSTMENT (gtk_adjustment_new (0.0, 0.0, 0.0, 0.0, 0.0, 0.0));
+
+  if (cell_map->hadj && (cell_map->hadj != hadj))
+    {
+      g_signal_handlers_disconnect_by_func (GTK_OBJECT (cell_map->hadj),
+					    update_adjustment, cell_map);
+      g_object_unref (cell_map->hadj);
+    }
+
+  if (cell_map->vadj && (cell_map->vadj != vadj))
+    {
+      g_signal_handlers_disconnect_by_func (GTK_OBJECT (cell_map->vadj),
+					    update_adjustment, cell_map);
+      g_object_unref (cell_map->vadj);
+    }
+
+  if (cell_map->hadj != hadj)
+    {
+      cell_map->hadj = hadj;
+      g_object_ref (cell_map->hadj);
+      gtk_object_sink (GTK_OBJECT (cell_map->hadj));
+
+      g_signal_connect (cell_map->hadj, "changed",
+			G_CALLBACK (update_adjustment), cell_map);
+      g_signal_connect (cell_map->hadj, "value_changed",
+			G_CALLBACK (update_adjustment), cell_map);
+
+      update_adjustment (hadj, cell_map);
+    }
+
+  if (cell_map->vadj != vadj)
+    {
+      cell_map->vadj = vadj;
+      g_object_ref (cell_map->vadj);
+      gtk_object_sink (GTK_OBJECT (cell_map->vadj));
+
+      g_signal_connect (cell_map->vadj, "changed",
+			G_CALLBACK (update_adjustment), cell_map);
+      g_signal_connect (cell_map->vadj, "value_changed",
+			G_CALLBACK (update_adjustment), cell_map);
+
+      update_adjustment (vadj, cell_map);
+    }
+}
+
+static void
+update_adjustment (GtkAdjustment *adj,
+		   OcfsCellMap   *cell_map)
+{
+  gfloat prev_val;
+
+  prev_val = adj->value;
+
+  adj->value = MIN (adj->value, adj->upper - adj->page_size);
+  adj->value = MAX (adj->value, 0.0);
+
+  if (adj->value != prev_val)
+    {
+      g_signal_handlers_block_by_func (adj, update_adjustment, cell_map);
+      gtk_adjustment_changed (adj);
+      g_signal_handlers_unblock_by_func (adj, update_adjustment, cell_map);
+    }
+
+  if (GTK_WIDGET_REALIZED (cell_map))
+    {
+      if (adj == cell_map->vadj)
+	gtk_widget_queue_draw (GTK_WIDGET (cell_map));
+      else
+	g_warning ("Horizontal scrolling not supported");
+    }
+}
+
+static void
+compute_vertical_scroll (OcfsCellMap *cell_map)
+{
+  gint width, height;
+  gint per_row, real_height;
+  gint old_value;
+
+  old_value = (gint) cell_map->vadj->value;
+
+  width  = GTK_WIDGET (cell_map)->allocation.width - 1;
+  height = GTK_WIDGET (cell_map)->allocation.height - 1;
+
+  per_row = width / cell_map->cell_width;
+  per_row = MAX (1, per_row);
+
+  real_height = (cell_map->map->len / per_row + 1) * cell_map->cell_height;
+
+  cell_map->vadj->upper = real_height;
+
+  cell_map->vadj->step_increment = MIN (cell_map->vadj->upper, cell_map->cell_height);
+  cell_map->vadj->page_increment = MIN (cell_map->vadj->upper, height - cell_map->cell_height * 2);
+  cell_map->vadj->page_size      = MIN (cell_map->vadj->upper, height);
+  cell_map->vadj->value          = MIN (cell_map->vadj->value, cell_map->vadj->upper - cell_map->vadj->page_size);
+  cell_map->vadj->value          = MAX (cell_map->vadj->value, 0.0);
+
+  g_signal_emit_by_name (cell_map->vadj, "changed");
+}
+
+#ifdef CELLMAP_TEST
+
+#define LENGTH 160
+
+int
+main (int    argc,
+      char **argv)
+{
+  GtkWidget  *window;
+  GtkWidget  *vbox;
+  GtkWidget  *scrl_win;
+  GtkWidget  *cell_map;
+  GtkWidget  *button;
+  OcfsBitmap *map;
+  guchar     *data;
+  gint        i;
+
+  gtk_init (&argc, &argv);
+
+  data = g_new (guchar, LENGTH);
+
+  for (i = 0; i < LENGTH; i++)
+    data[i] = i % 2 ? 0xff : 0x00;
+
+  map = ocfs_bitmap_new (data, LENGTH);
+
+  window = g_object_connect (g_object_new (GTK_TYPE_WINDOW,
+					   "type", GTK_WINDOW_TOPLEVEL,
+					   "border_width", 5,
+					   NULL),
+			     "signal::delete-event", gtk_main_quit, NULL,
+			     NULL);
+
+  vbox = gtk_vbox_new (FALSE, 5);
+  gtk_container_add (GTK_CONTAINER (window), vbox);
+
+  scrl_win = g_object_new (GTK_TYPE_SCROLLED_WINDOW,
+			   "hscrollbar_policy", GTK_POLICY_NEVER,
+			   "vscrollbar_policy", GTK_POLICY_ALWAYS,
+			   "parent", vbox,
+			   NULL);
+
+  cell_map = g_object_new (OCFS_TYPE_CELL_MAP,
+			   "map", map,
+			   "parent", scrl_win,
+			   NULL);
+
+  button = g_object_connect (g_object_new (GTK_TYPE_BUTTON,
+					   "label", "Whee!",
+					   NULL),
+			     "signal::clicked", gtk_main_quit, NULL,
+			     NULL);
+  gtk_box_pack_end (GTK_BOX (vbox), button, FALSE, FALSE, 0);
+
+  gtk_widget_show_all (window);
+
+  gtk_main ();
+
+  return 0;
+}
+#endif

Copied: trunk/ocfs2tool/ocfscellmap.h (from rev 256, trunk/ocfstool/ocfscellmap.h)
===================================================================
--- trunk/ocfstool/ocfscellmap.h	2004-09-24 23:55:36 UTC (rev 256)
+++ trunk/ocfs2tool/ocfscellmap.h	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,78 @@
+/*
+ * ocfscellmap.h
+ *
+ * Function prototypes for related 'C' file.
+ *
+ * Copyright (C) 2002 Oracle Corporation.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 021110-1307, USA.
+ *
+ * Author: Manish Singh
+ */
+
+#ifndef __OCFS_CELL_MAP_H__
+#define __OCFS_CELL_MAP_H__
+
+
+#include <gtk/gtk.h>
+
+#include "ocfsbitmap.h"
+
+
+#define OCFS_TYPE_CELL_MAP            (ocfs_cell_map_get_type ())
+#define OCFS_CELL_MAP(obj)            (G_TYPE_CHECK_INSTANCE_CAST ((obj), OCFS_TYPE_CELL_MAP, OcfsCellMap))
+#define OCFS_CELL_MAP_CLASS(klass)    (G_TYPE_CHECK_CLASS_CAST ((klass), OCFS_TYPE_CELL_MAP, OcfsCellMapClass))
+#define OCFS_IS_CELL_MAP(obj)         (G_TYPE_CHECK_INSTANCE_TYPE ((obj), OCFS_TYPE_CELL_MAP))
+#define OCFS_IS_CELL_MAP_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), OCFS_TYPE_CELL_MAP))
+#define OCFS_CELL_MAP_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), OCFS_TYPE_CELL_MAP, OcfsCellMapCLass))
+
+
+typedef struct _OcfsCellMap      OcfsCellMap;
+typedef struct _OcfsCellMapClass OcfsCellMapClass;
+
+struct _OcfsCellMap
+{
+  GtkDrawingArea  parent_instance;
+
+  OcfsBitmap     *map;
+
+  gint            cell_width;
+  gint            cell_height;
+
+  GtkAdjustment  *hadj;
+  GtkAdjustment  *vadj;
+};
+
+struct _OcfsCellMapClass
+{
+  GtkDrawingAreaClass parent_class;
+
+  void  (*set_scroll_adjustments) (OcfsCellMap   *bd,
+				   GtkAdjustment *hadjustment,
+				   GtkAdjustment *vadjustment);
+};
+
+
+GType      ocfs_cell_map_get_type       (void);
+GtkWidget *ocfs_cell_map_new            (OcfsBitmap  *map);
+void       ocfs_cell_map_set_map        (OcfsCellMap *cell_map,
+					 OcfsBitmap  *map);
+void       ocfs_cell_map_set_cell_props (OcfsCellMap *cell_map,
+					 gint         cell_width,
+					 gint         cell_height);
+
+
+#endif /* __OCFS_CELL_MAP_H__ */

Added: trunk/ocfs2tool/ocfsmarshal.list
===================================================================
--- trunk/ocfs2tool/ocfsmarshal.list	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/ocfsmarshal.list	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1 @@
+VOID: OBJECT, OBJECT

Copied: trunk/ocfs2tool/ocfsplist.c (from rev 256, trunk/ocfstool/ocfsplist.c)
===================================================================
--- trunk/ocfstool/ocfsplist.c	2004-09-24 23:55:36 UTC (rev 256)
+++ trunk/ocfs2tool/ocfsplist.c	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,331 @@
+/*
+ * ocfsplist.c
+ *
+ * Create a list of valid partitions
+ *
+ * Copyright (C) 2002 Oracle Corporation.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 021110-1307, USA.
+ *
+ * Author: Manish Singh
+ */
+
+#include <ctype.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#include <fcntl.h>
+
+#include <glib.h>
+
+#include "ocfs2.h"
+
+#include "ocfsplist.h"
+
+
+typedef struct _BuildData BuildData;
+
+struct _BuildData
+{
+  gboolean  unmounted;
+  GList    *list;
+};
+
+
+static gboolean check_partition_type (const gchar *device,
+				      OcfsFSType  *type);
+static gboolean valid_device         (const gchar *device,
+				      gboolean     no_ocfs_check,
+				      OcfsFSType  *type);
+static void     partition_info_fill  (GHashTable  *info);
+static gboolean list_builder         (gpointer     key,
+				      gpointer     value,
+				      gpointer     user_data);
+
+
+static gboolean
+check_partition_type (const gchar *device,
+		      OcfsFSType  *type)
+{
+  errcode_t      ret;
+  ocfs2_filesys *fs;
+
+  ret = ocfs2_open (device, OCFS2_FLAG_RO, 0, 0, &fs);
+
+  if (ret)
+    {
+      if (ret == OCFS2_ET_OCFS_REV)
+	*type = OCFS_FS_TYPE_OCFS;
+      else
+	return FALSE;
+    }
+  else
+    *type = OCFS_FS_TYPE_OCFS2;
+
+  ocfs2_close (fs);
+  return TRUE;
+}
+
+static gboolean
+valid_device (const gchar *device,
+	      gboolean     no_ocfs_check,
+	      OcfsFSType  *type)
+{
+  gboolean     is_bad = FALSE;
+  struct stat  sbuf;
+  FILE        *f;
+  gchar        buf[100], *proc, *d;
+  gint         i, fd;
+
+  if ((stat (device, &sbuf) != 0) ||
+      (!S_ISBLK (sbuf.st_mode)) ||
+      ((sbuf.st_mode & 0222) == 0))
+    return FALSE;
+
+  if (strncmp ("/dev/hd", device, 7) == 0)
+    {
+      i = strlen (device) - 1;
+      while (i > 5 && isdigit (device[i]))
+	i--;
+
+      d =  g_strndup (device + 5, i + 1);
+      proc = g_strconcat ("/proc/ide/", d, "/media", NULL);
+      g_free (d);
+
+      f = fopen (proc, "r");
+      g_free (proc);
+
+      if (f != NULL && fgets (buf, sizeof (buf), f))
+	is_bad = ((strncmp (buf, "cdrom", 5) == 0) ||
+		  (strncmp (buf, "tape",  4) == 0));
+
+      if (f)
+	fclose (f);
+     
+      if (is_bad)
+	return FALSE; 
+    }
+
+#ifndef DEVEL_MACHINE
+  fd = open (device, O_RDWR);
+  if (fd == -1)
+    return FALSE;
+  close (fd);
+
+  return no_ocfs_check ? TRUE : check_partition_type (device, type);
+#else
+  fd = 0;
+  *type = OCFS_FS_TYPE_OCFS2;
+  return TRUE;
+#endif
+}
+
+static void
+partition_info_fill (GHashTable *info)
+{
+  FILE   *proc;
+  gchar   line[100], name[100], *device;
+  GSList *list;
+  gint    i;
+  gchar  *p;
+
+  proc = fopen ("/proc/partitions", "r");
+  if (proc == NULL)
+    return;
+
+  while (fgets (line, sizeof(line), proc) != NULL)
+    {
+      if (sscanf(line, "%*d %*d %*d %99[^ \t\n]", name) != 1)
+	continue;
+
+      device = g_strconcat ("/dev/", name, NULL);
+
+      i = strlen (device) - 1;
+      if (isdigit (device[i]))
+	{
+	  while (i > 0 && isdigit (device[i]))
+	    i--;
+
+	  p = g_strndup (device, i + 1);
+	  list = g_hash_table_lookup (info, p);
+
+	  if (list == NULL)
+	    {
+	      list = g_slist_prepend (NULL, device);
+	      g_hash_table_insert (info, p, list);
+	    }
+	  else
+	    {
+	      if (strcmp (p, list->data) == 0)
+		{
+		  g_free (list->data);
+		  list->data = device;
+		}
+	      else
+		g_slist_append (list, device);
+
+	      g_free (p);
+	    }
+	}
+      else if (!g_hash_table_lookup (info, device))
+	{
+	  list = g_slist_prepend (NULL, g_strdup (device));
+	  g_hash_table_insert (info, device, list);
+	}
+      else
+	g_free (device);
+    }
+
+  fclose (proc);
+}
+
+static gboolean
+list_builder (gpointer key,
+	      gpointer value,
+	      gpointer user_data)
+{
+  BuildData         *bdata;
+  GSList            *list, *last;
+  gchar             *device;
+  gchar              mountpoint[PATH_MAX];
+  OcfsPartitionInfo *info;
+  gint               flags;
+  OcfsFSType         type;
+  errcode_t          ret;
+
+  bdata = user_data;
+  list = value;
+
+  while (list)
+    {
+      device = list->data;
+
+      if (valid_device (device, bdata->unmounted, &type))
+	{
+	  info = g_new (OcfsPartitionInfo, 1);
+
+	  info->device = g_strdup (device);
+	  info->type = type;
+
+	  ret = ocfs2_check_mount_point (device, &flags, mountpoint, PATH_MAX);
+
+	  if (ret == 0)
+	    {
+	      if (flags & OCFS2_MF_MOUNTED)
+		info->mountpoint = g_strdup (mountpoint);
+	      else
+		info->mountpoint = NULL;
+	    }
+	  else
+	    info->mountpoint = NULL;
+
+	  if (bdata->unmounted)
+	    {
+	      if (info->mountpoint)
+		{
+		  g_free (info->mountpoint);
+		  g_free (info->device);
+		}
+	      else
+		bdata->list = g_list_prepend (bdata->list, info->device);
+
+	      g_free (info);
+	    }
+	  else
+	    bdata->list = g_list_prepend (bdata->list, info);
+	}
+
+      last = list;
+      list = list->next;
+
+      g_free (device);
+      g_slist_free_1 (last);
+    }
+
+  g_free (key);
+
+  return TRUE;
+}
+
+#ifdef LIST_TEST_HASH
+static void
+print_hash (gpointer key,
+	    gpointer value,
+	    gpointer user_data)
+{
+  GSList *list;
+
+  g_print ("Key: %s; Values:", (gchar *) key);
+  for (list = value; list != NULL; list = list->next)
+    g_print (" %s", (gchar *) list->data);
+  g_print ("\n");
+}
+#endif
+
+GList *
+ocfs_partition_list (gboolean unmounted)
+{
+  GHashTable *info;
+  BuildData   bdata = { unmounted, NULL };
+
+  info = g_hash_table_new (g_str_hash, g_str_equal);
+
+  partition_info_fill (info);
+
+#ifdef LIST_TEST_HASH
+  g_hash_table_foreach (info, print_hash, NULL);
+#endif
+
+  g_hash_table_foreach_remove (info, list_builder, &bdata);
+  
+  g_hash_table_destroy (info);
+
+  return bdata.list;
+}
+
+#ifdef LIST_TEST
+int
+main (int    argc,
+      char **argv)
+{
+  GList             *plist, *list;
+  OcfsPartitionInfo *info;
+
+  g_print ("All:\n");
+
+  plist = ocfs_partition_list (FALSE);
+  
+  for (list = plist; list; list = list->next)
+    {
+      info = list->data;
+      g_print ("Device: %s; Mountpoint %s; Type %s\n",
+	       info->device, info->mountpoint,
+	       info->type == OCFS_FS_TYPE_OCFS2 ? "ocfs2" : "ocfs");
+    }
+
+  g_print ("Unmounted:\n");
+
+  plist = ocfs_partition_list (TRUE);
+  
+  for (list = plist; list; list = list->next)
+    g_print ("Device: %s\n", (gchar *) list->data);
+
+  return 0;
+}
+#endif

Copied: trunk/ocfs2tool/ocfsplist.h (from rev 256, trunk/ocfstool/ocfsplist.h)
===================================================================
--- trunk/ocfstool/ocfsplist.h	2004-09-24 23:55:36 UTC (rev 256)
+++ trunk/ocfs2tool/ocfsplist.h	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,51 @@
+/*
+ * ocfsplist.h
+ *
+ * Function prototypes for related 'C' file.
+ *
+ * Copyright (C) 2002 Oracle Corporation.  All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public
+ * License along with this program; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 021110-1307, USA.
+ *
+ * Author: Manish Singh
+ */
+
+#ifndef __OCFS_PARTITION_LIST_H__
+#define __OCFS_PARTITION_LIST_H__
+
+#include <glib.h>
+
+
+typedef enum
+{
+  OCFS_FS_TYPE_OCFS,
+  OCFS_FS_TYPE_OCFS2
+} OcfsFSType;
+
+typedef struct _OcfsPartitionInfo OcfsPartitionInfo;
+
+struct _OcfsPartitionInfo
+{
+  gchar      *device;
+  gchar      *mountpoint;
+  OcfsFSType  type;
+};
+
+
+GList *ocfs_partition_list (gboolean     unmounted);
+
+
+#endif /* __OCFS_PARTITION_LIST_H__ */

Added: trunk/ocfs2tool/process.py
===================================================================
--- trunk/ocfs2tool/process.py	2004-09-27 02:57:27 UTC (rev 260)
+++ trunk/ocfs2tool/process.py	2004-09-27 05:59:59 UTC (rev 261)
@@ -0,0 +1,152 @@
+import os
+import types
+import fcntl
+import popen2
+
+import gobject
+import gtk
+
+from guiutil import set_props
+
+INTERVAL = 100
+TIMEOUT = 10000
+
+class Process:
+    def __init__(self, command, title, desc, parent=None, spin_now=True):
+        if isinstance(command, types.StringTypes):
+            if len(command.split(None, 1)) < 2:
+                command = (command,)
+
+        self.command = command
+
+        self.title = title
+        self.desc = desc
+
+        self.parent = parent
+
+        self.spin_now = spin_now
+
+        self.pipe = popen2.Popen4(self.command)
+
+    def reap(self):
+        self.success = False
+        self.killed = False
+
+        self.count = TIMEOUT // INTERVAL
+        self.threshold = self.count - INTERVAL * 10
+
+        self.dialog = None
+
+        if self.spin_now:
+            self.count = TIMEOUT * 60
+            self.make_progress_box()
+
+        timeout_id = gobject.timeout_add(INTERVAL, self.timeout)
+
+        fromchild = self.pipe.fromchild
+
+        fileno = fromchild.fileno()
+        flags = fcntl.fcntl(fileno, fcntl.F_GETFL, 0)
+        flags = flags | os.O_NONBLOCK
+        fcntl.fcntl(fileno, fcntl.F_SETFL, flags)
+
+        self.output = ''
+        output_id = gobject.io_add_watch(fromchild, gobject.IO_IN, self.read)
+
+        gtk.main()
+
+        if self.dialog:
+            self.dialog.destroy()
+
+        gobject.source_remove(output_id)
+        gobject.source_remove(timeout_id)
+
+        if not self.success:
+            if self.killed:
+                if self.output:
+                    self.output += '\n'
+
+                self.output += 'Killed prematurely.'
+
+        return self.success, self.output, self.killed
+
+    def timeout(self):
+        self.count = self.count - 1
+
+        ret = self.pipe.poll()
+
+        if ret != -1:
+            self.success = not os.WEXITSTATUS(ret)
+            gtk.main_quit()
+            return True
+
+        if self.count < 1:
+            self.kill()
+            return True
+
+        if self.count < self.threshold and not self.dialog:
+            self.make_progess_box()
+
+        if self.dialog:
+            self.pbar.pulse()
+
+        return True
+
+    def kill(self):
+        self.success = False
+        self.killed = True
+
+        os.kill(self.pipe.pid, 15)
+        gobject.timeout_add(INTERVAL * 5, self.kill_timeout)
+
+        gtk.main_quit()
+
+    def kill_timeout(self):
+        if self.pipe.poll() == -1:
+            os.kill(self.pipe.pid, 9)
+            self.kill_9 = True
+
+        return False
+
+    def make_progress_box(self):
+        self.dialog = gtk.Window()
+        set_props(self.dialog, title=self.title,
+                               resizable=False,
+                               modal=True,
+                               type_hint=gtk.gdk.WINDOW_TYPE_HINT_DIALOG)
+
+        def ignore(w, e):
+            return True
+        self.dialog.connect('delete-event', ignore)
+
+        self.dialog.set_transient_for(self.parent)
+
+        vbox = gtk.VBox()
+        set_props(vbox, spacing=0,
+                        homogeneous=False,
+                        border_width=4,
+                        parent=self.dialog)
+
+        label = gtk.Label(self.desc + '...')
+        vbox.pack_start(label, expand=False, fill=False)
+
+        self.pbar = gtk.ProgressBar()
+        vbox.pack_start(self.pbar, expand=False, fill=False)
+
+        self.dialog.show_all()
+
+    def read(self, fd, cond):
+        if cond & gtk.gdk.INPUT_READ:
+            try:
+                self.output += fd.read(1024)
+            except IOError, e:
+                return False
+
+        return True
+
+def main():
+    process = Process('echo Hello; sleep 10', 'Sleep', 'Sleeping')
+    print process.reap()
+
+if __name__ == '__main__':
+    main() 



More information about the Ocfs2-tools-commits mailing list