hal: Branch 'master' - 2 commits

David Zeuthen david at kemper.freedesktop.org
Wed Jan 10 12:01:08 PST 2007


 configure.in                                        |   29 ++
 fdi/policy/10osvendor/10-dell-laptop-brightness.fdi |   43 +++
 fdi/policy/10osvendor/Makefile.am                   |    4 
 hald/linux/addons/Makefile.am                       |    6 
 hald/linux/addons/addon-dell-backlight.cpp          |  252 ++++++++++++++++++++
 hald/logger.h                                       |    9 
 6 files changed, 343 insertions(+)

New commits:
diff-tree 69353b9c50d4da892f5bdd1cd75aa587870baada (from 477c8294bf988a70f05d324d308cb89734ff3dba)
Author: David Zeuthen <davidz at redhat.com>
Date:   Wed Jan 10 15:01:04 2007 -0500

    fix up libsmbios detection

diff --git a/configure.in b/configure.in
index 9ae0864..2af5a01 100644
--- a/configure.in
+++ b/configure.in
@@ -246,7 +246,9 @@ else
 fi
 
 dnl Check for libsmbios 
-AC_CHECK_LIB(smbios, SMBIOSFreeMemory, [AM_CONDITIONAL(HAVE_SMBIOS, true)], [AM_CONDITIONAL(HAVE_SMBIOS, false)])
+AC_CHECK_LIB(smbios, SMBIOSFreeMemory, [
+		     USE_SMBIOS=yes; AM_CONDITIONAL(HAVE_SMBIOS,true)], [
+		     USE_SMBIOS=no; AM_CONDITIONAL(HAVE_SMBIOS,false)])
 
 dnl Check for libpci
 AC_CHECK_HEADERS(pci/pci.h, [
@@ -585,7 +587,7 @@ BUILD_DELL=no
 if test "x$with_dell_backlight" = "xyes" ; then
    BUILD_DELL=yes
 elif test "x$with_dell_backlight" = "x" ; then
-  if test "$HAVE_SMBIOS" != "false" ; then
+  if test "$USE_SMBIOS" = "yes" ; then
     case "${HALD_BACKEND}" in
       linux)
         case "${host}" in
diff-tree 477c8294bf988a70f05d324d308cb89734ff3dba (from 479ea978bb394cc36f4d5bd35cc96f9e71d4fff9)
Author: Erik Andrén <erik.andren at gmail.com>
Date:   Wed Jan 10 14:36:16 2007 -0500

    add addon for backlight control on Dell computers
    
    I've developed an addon for hal, making it possible to control the AC
    and the battery backlight values for Dell laptops using SMBIOS.
    
    My first approach was to try to emulate the work the c++ libsmbios
    library developed by Dell did in C. I quickly discovered  that the code
    got quite messy and thus I decided to abandon this approach in favor of
    linking against the libsmbios library. This of course meant that I
    needed to write the addon in c++. (I don't know if there is a policy in
    the hal development against having c++-programs shipped).
    Anyway, I got away with this implementation rather cheaply, only needing
    to introduce a slight modification to logger.h in hald/
    
    The addon currently works quite well for me but I still have the
    following issues:
    
    1. There seems to be something funky going on in gnome-power-manager
    while changing the brightness in battery mode. It thinks the current
    level is 7 all the time. This bug is problably related to the
    gnome-power-manager as the Power Manager Brightness Applet works correctly.
    
    2. Brightness turnaround speed isn't great. It's definitely an
    improvement when
    compared with the patch developed by Richard Hughes in July but when
    going from 7 (highest) to 0 (lowest) you can definitely feel the lag.
    
    3. No support for if you have protected you bios with a password. It's
    quite possible to workaround this issue by adding some kind of a
    mechanism throwing an exception prompting for the password. This
    problably need to be coordinated with gnome-power-manager.
    
    The attached patch cleanly applies to current git.
    
    Please comment.
    
    /With kind regards
    Erik Andrén

diff --git a/configure.in b/configure.in
index 5eaf375..9ae0864 100644
--- a/configure.in
+++ b/configure.in
@@ -245,6 +245,9 @@ else
 	AM_CONDITIONAL(HAVE_LIBUSB,false)
 fi
 
+dnl Check for libsmbios 
+AC_CHECK_LIB(smbios, SMBIOSFreeMemory, [AM_CONDITIONAL(HAVE_SMBIOS, true)], [AM_CONDITIONAL(HAVE_SMBIOS, false)])
+
 dnl Check for libpci
 AC_CHECK_HEADERS(pci/pci.h, [
 	AC_CHECK_LIB(pci, pci_init, [
@@ -576,6 +579,29 @@ elif test "x$with_usb_csr" = "x" ; then
 fi
 AM_CONDITIONAL(BUILD_USBCSR, test x$BUILD_USBCSR = xyes)
 
+dnl Dell backlight 
+AC_ARG_WITH(dell-backlight,     [  --with-dell-backlight   Whether to build Dell backlight support (auto)])
+BUILD_DELL=no
+if test "x$with_dell_backlight" = "xyes" ; then
+   BUILD_DELL=yes
+elif test "x$with_dell_backlight" = "x" ; then
+  if test "$HAVE_SMBIOS" != "false" ; then
+    case "${HALD_BACKEND}" in
+      linux)
+        case "${host}" in
+	  i[[3456]]86-*-*)
+            BUILD_DELL=yes
+	    ;;
+	  *)
+	    ;;
+	esac
+        ;;
+      *)
+        ;;
+    esac
+   fi
+fi
+AM_CONDITIONAL(BUILD_DELL, test x$BUILD_DELL = xyes)
 
 dnl
 dnl SUBSETTING END
@@ -670,6 +696,7 @@ echo "
         Macbook Pro utils:          ${BUILD_MACBOOKPRO} (Linux only, x86 only, requires libpci)
         CPU frequency scaling:      ${BUILD_CPUFREQ} (Linux only)
 	USB wireless mouse power:   ${BUILD_USBCSR} (Linux only, requires libusb)
+	Dell Backlight              ${BUILD_DELL} (Linux only, requires libsmbios)
 
         Maintainer mode:            ${USE_MAINTAINER_MODE}
         Building verbose mode:      ${enable_verbose_mode}
diff --git a/fdi/policy/10osvendor/10-dell-laptop-brightness.fdi b/fdi/policy/10osvendor/10-dell-laptop-brightness.fdi
new file mode 100644
index 0000000..b3f710f
--- /dev/null
+++ b/fdi/policy/10osvendor/10-dell-laptop-brightness.fdi
@@ -0,0 +1,43 @@
+<?xml version="1.0" encoding="UTF-8"?>
+
+<deviceinfo version="0.2">
+
+  <!-- This is for controlling LCD brightness on DELL computers.
+       DELL require the use of libsmbios to control the panel together with the dcdbas kernel module.
+       You will need at least version 0.12.1 of libsmbios.
+       NOTE: You will need to remove both Primary AND Admin Passwords for this
+       to work correctly.
+       See http://bugs.freedesktop.org/show_bug.cgi?id=7221 for details. -->
+  <device>
+    <match key="system.kernel.name" string="Linux"> 
+      <match key="smbios.system.manufacturer" string="Dell Computer Corporation">
+        <match key="system.formfactor" string="laptop">
+           <spawn udi="/org/freedesktop/Hal/devices/dell_lcd_panel"/>
+        </match>
+      </match>
+    </match>
+  </device>
+
+  <device>
+    <match key="system.kernel.name" string="Linux"> 
+      <match key="smbios.system.manufacturer" string="Dell Inc.">
+        <match key="system.formfactor" string="laptop">
+           <spawn udi="/org/freedesktop/Hal/devices/dell_lcd_panel"/>
+        </match>
+      </match>
+    </match>
+  </device>
+
+  <device>
+    <match key="info.udi" string="/org/freedesktop/Hal/devices/dell_lcd_panel">
+      <append key="info.capabilities" type="strlist">laptop_panel</append>
+      <merge key="info.category" type="string">laptop_panel</merge>
+      <merge key="info.product" type="string">Dell Laptop Panel</merge>
+      <merge key="laptop_panel.access_method" type="string">custom</merge>
+      <merge key="laptop_panel.num_levels" type="int">8</merge>
+      <merge key="laptop_panel.brightness_in_hardware" type="bool">false</merge>
+      <append key="info.addons" type="strlist">hald-addon-dell-backlight</append>
+    </match>
+  </device>
+
+</deviceinfo>
\ No newline at end of file
diff --git a/fdi/policy/10osvendor/Makefile.am b/fdi/policy/10osvendor/Makefile.am
index af2332c..734eead 100644
--- a/fdi/policy/10osvendor/Makefile.am
+++ b/fdi/policy/10osvendor/Makefile.am
@@ -25,6 +25,10 @@ if BUILD_N770
 dist_fdi_DATA += 10-nokia770-backlight.fdi
 endif
 
+if BUILD_DELL
+dist_fdi_DATA += 10-dell-laptop-brightness.fdi
+endif
+
 check:
 	for f in $(dist_fdi_DATA); do \
             echo -n "Validate XML in $$f : "; \
diff --git a/hald/linux/addons/Makefile.am b/hald/linux/addons/Makefile.am
index eb5496e..7c8c5d9 100644
--- a/hald/linux/addons/Makefile.am
+++ b/hald/linux/addons/Makefile.am
@@ -48,6 +48,12 @@ libexec_PROGRAMS += hald-addon-usb-csr
 hald_addon_usb_csr_SOURCES = addon-usb-csr.c ../../logger.c ../../util_helper.c
 hald_addon_usb_csr_LDADD = $(top_builddir)/libhal/libhal.la -lusb @GLIB_LIBS@
 endif
+
+if BUILD_DELL
+libexec_PROGRAMS += hald-addon-dell-backlight
+hald_addon_dell_backlight_SOURCES = addon-dell-backlight.cpp ../../logger.c 
+hald_addon_dell_backlight_LDADD = $(top_builddir)/libhal/libhal.la -lsmbios @GLIB_LIBS@ 
+endif
 endif
 
 hald_addon_acpi_SOURCES = addon-acpi.c ../../logger.c ../../util_helper.c
diff --git a/hald/linux/addons/addon-dell-backlight.cpp b/hald/linux/addons/addon-dell-backlight.cpp
new file mode 100644
index 0000000..254d492
--- /dev/null
+++ b/hald/linux/addons/addon-dell-backlight.cpp
@@ -0,0 +1,252 @@
+/***************************************************************************
+ * 
+ *
+ * addon-dell-backlight.cpp : Sets the backlight for Dell laptops using the libsmbios interface
+ * 
+ * Copyright (C) 2007 Erik Andrén <erik.andren at gmail.com>
+ * Heavily based on the macbook addon and the dellLcdBrightness code in libsmbios. 
+ * This program needs the dcdbas module to be loaded and libsmbios >= 0.12.1 installed
+ * 
+ * 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., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ *
+ **************************************************************************/
+
+#include <glib/gmain.h>
+#include <dbus/dbus-glib.h>
+#include <dbus/dbus-glib-lowlevel.h>
+
+#include "libhal/libhal.h"
+#include "../../logger.h"
+
+#include "smbios/ISmi.h"
+#include "smbios/IToken.h"
+
+static LibHalContext *halctx = NULL;
+static GMainLoop *main_loop;
+static char *udi;
+static DBusConnection *conn;
+static const int DELL_LCD_BRIGHTNESS_TOKEN = 0x007d;
+
+using namespace std;
+using namespace smi;
+
+typedef u32 (*readfn)(u32 location, u32 *minValue, u32 *maxValue);
+typedef u32 (*writefn)(const std::string &password, u32 location, u32 value, u32 *minValue, u32 *maxValue);
+
+static u32 
+read_backlight(dbus_bool_t ACon)
+{
+	u8  location = 0;
+	u32 minValue = 0;
+	u32 maxValue = 0;
+	u32 curValue;
+	readfn readFunction;
+	
+	if (ACon) 
+                readFunction = &smi::readACModeSetting;
+    	else 
+                readFunction = &smi::readBatteryModeSetting;
+	
+	smbios::TokenTableFactory *ttFactory = smbios::TokenTableFactory::getFactory() ;
+        smbios::ITokenTable *tokenTable = ttFactory->getSingleton();
+        smbios::IToken *token = &(*((*tokenTable)[ DELL_LCD_BRIGHTNESS_TOKEN ]));
+        dynamic_cast< smbios::ISmiToken * >(token)->getSmiDetails( static_cast<u16*>(0), static_cast<u8*>(0), &location );
+
+	try 
+	{ 
+        	curValue = readFunction(location, &minValue, &maxValue);
+	}
+	catch( const exception &e ) 
+	{
+        	HAL_ERROR(("Could not access the dcdbas kernel module. Please make sure it is loaded"));
+		return 7;
+    	}
+
+	if(ACon) 
+		HAL_DEBUG(("Reading %d from the AC backlight register", curValue));	
+	else 
+		HAL_DEBUG(("Reading %d from the BAT backlight register", curValue));
+
+	return curValue;
+}
+
+static void 
+write_backlight (u32 newBacklightValue, dbus_bool_t ACon) 
+{	
+	u8  location = 0;
+	u32 minValue = 0;
+	u32 maxValue = 0;	
+	u32 curValue;
+	writefn writeFunction;
+	string password(""); //FIXME: Implement password support
+	
+	if (ACon) 
+                writeFunction = &smi::writeACModeSetting;
+    	else 
+                writeFunction = &smi::writeBatteryModeSetting;
+
+	smbios::TokenTableFactory *ttFactory = smbios::TokenTableFactory::getFactory();
+        smbios::ITokenTable *tokenTable = ttFactory->getSingleton();
+        smbios::IToken *token = &(*((*tokenTable)[ DELL_LCD_BRIGHTNESS_TOKEN ]));
+        dynamic_cast< smbios::ISmiToken * >(token)->getSmiDetails( static_cast<u16*>(0), static_cast<u8*>(0), &location );
+
+	try 
+	{
+		curValue = writeFunction(password, location, newBacklightValue, &minValue, &maxValue); 
+	}
+	catch( const exception &e )
+    	{
+        	HAL_ERROR(("Could not access the dcdbas kernel module. Please make sure it is loaded"));
+		return;
+    	}
+	if(ACon)
+		HAL_DEBUG(("Wrote %d to the AC backlight", curValue));
+	else
+		HAL_DEBUG(("Wrote %d to the BAT backlight", curValue));
+}
+
+static DBusHandlerResult
+filter_function (DBusConnection *connection, DBusMessage *message, void *userdata)
+{
+	DBusError err;
+	DBusMessage *reply = NULL;
+	dbus_bool_t AC;
+	dbus_error_init (&err);
+
+	/* Mechanism to ensure that we always set the AC brightness when we are on AC-power etc. */
+	AC = libhal_device_get_property_bool (halctx, 
+					     "/org/freedesktop/Hal/devices/acpi_AC",
+					     "ac_adapter.present",
+					     &err);
+
+	if (dbus_message_is_method_call (message, 
+					 "org.freedesktop.Hal.Device.LaptopPanel", 
+					 "SetBrightness")) {
+		int brightness;
+		
+		HAL_DEBUG(("Received SetBrightness DBus call"));
+
+		if (dbus_message_get_args (message, 
+					   &err,
+					   DBUS_TYPE_INT32, &brightness,
+					   DBUS_TYPE_INVALID)) {
+			if (brightness < 0 || brightness > 7) {
+				reply = dbus_message_new_error (message,
+								"org.freedesktop.Hal.Device.LaptopPanel.Invalid",
+								"Brightness has to be between 0 and 7!");
+
+			} else {
+				int return_code;
+				
+				write_backlight (brightness, AC);
+
+				reply = dbus_message_new_method_return (message);
+				if (reply == NULL)
+					goto error;
+
+				return_code = 0;
+
+				dbus_message_append_args (reply,
+							  DBUS_TYPE_INT32, &return_code,
+							  DBUS_TYPE_INVALID);
+			}
+
+			dbus_connection_send (connection, reply, NULL);
+		}
+		
+	} else if (dbus_message_is_method_call (message, 
+						"org.freedesktop.Hal.Device.LaptopPanel", 
+						"GetBrightness")) {
+		HAL_DEBUG(("Received GetBrightness DBUS call"));
+		
+		if (dbus_message_get_args (message, 
+					   &err,
+					   DBUS_TYPE_INVALID)) {
+			int brightness = read_backlight(AC);
+			if (brightness < 0)
+				brightness = 0;
+			else if (brightness > 7)
+				brightness = 7;
+
+			reply = dbus_message_new_method_return (message);
+			if (reply == NULL)
+				goto error;
+
+			dbus_message_append_args (reply,
+						  DBUS_TYPE_INT32, &brightness,
+						  DBUS_TYPE_INVALID);
+			dbus_connection_send (connection, reply, NULL);
+		}
+	}	
+error:
+	if (reply != NULL)
+		dbus_message_unref (reply);
+	
+	return DBUS_HANDLER_RESULT_HANDLED;
+}
+
+int
+main (int argc, char *argv[])
+{
+ 	DBusError err;
+
+	setup_logger ();
+
+	udi = getenv ("UDI");
+
+	HAL_DEBUG (("udi=%s", udi));
+	if (udi == NULL) {
+		HAL_ERROR (("No device specified"));
+		return -2;
+	}
+
+	dbus_error_init (&err);
+	if ((halctx = libhal_ctx_init_direct (&err)) == NULL) {
+		HAL_ERROR (("Cannot connect to hald"));
+		return -3;
+	}
+
+	dbus_error_init (&err);
+	if (!libhal_device_addon_is_ready (halctx, udi, &err)) {
+		return -4;
+	}
+
+	conn = libhal_ctx_get_dbus_connection (halctx);
+	dbus_connection_setup_with_g_main (conn, NULL);
+
+	dbus_connection_add_filter (conn, filter_function, NULL, NULL);
+
+	/* this works because we hardcoded the udi's in the <spawn> in the fdi files */
+	if (!libhal_device_claim_interface (halctx, 
+					    "/org/freedesktop/Hal/devices/dell_lcd_panel", 
+					    "org.freedesktop.Hal.Device.LaptopPanel", 
+					    "    <method name=\"SetBrightness\">\n"
+					    "      <arg name=\"brightness_value\" direction=\"in\" type=\"i\"/>\n"
+					    "      <arg name=\"return_code\" direction=\"out\" type=\"i\"/>\n"
+					    "    </method>\n"
+					    "    <method name=\"GetBrightness\">\n"
+					    "      <arg name=\"brightness_value\" direction=\"out\" type=\"i\"/>\n"
+					    "    </method>\n",
+					    &err)) {
+		HAL_ERROR (("Cannot claim interface 'org.freedesktop.Hal.Device.LaptopPanel'"));
+		return -4;
+	}
+	
+	main_loop = g_main_loop_new (NULL, FALSE);
+	g_main_loop_run (main_loop);
+	return 0;
+}
+
+
diff --git a/hald/logger.h b/hald/logger.h
index 1503f7b..8e6cd96 100644
--- a/hald/logger.h
+++ b/hald/logger.h
@@ -23,6 +23,10 @@
  *
  **************************************************************************/
 
+#ifdef __cplusplus
+extern "C" {
+#endif
+
 #ifndef LOGGER_H
 #define LOGGER_H
 
@@ -85,3 +89,8 @@ void setup_logger (void);
 /** @} */
 
 #endif				/* LOGGER_H */
+
+#ifdef __cplusplus
+}
+#endif
+


More information about the hal-commit mailing list