Bug 9721

Summary: macbook lcp panel
Product: hal Reporter: Eloi Primaux <eloi>
Component: haldAssignee: David Zeuthen (not reading bugmail) <zeuthen>
Status: REOPENED --- QA Contact:
Severity: normal    
Priority: high CC: stephan.michels
Version: unspecified   
Hardware: x86 (IA32)   
OS: Linux (All)   
Whiteboard:
i915 platform: i915 features:

Description Eloi Primaux 2007-01-20 15:12:01 UTC
hi, i tried to make hal work on macbook non pro lcp panel
i added some line in few files as following:

10-laptop-panel-mgmt-policy.fdi: (after macbook pro definition)

  <!-- this is for Macbook non Pro (LCD panel only) -->
  <device>
    <match key="system.kernel.name" string="Linux">
      <match key="smbios.system.manufacturer" string="Apple Computer, Inc.">
        <match key="smbios.system.product" string="MacBook1,1">
          <spawn udi="/org/freedesktop/Hal/devices/macbook_lcd_panel"/>
        </match>
      </match>
    </match>
  </device>
  <device>
    <match key="info.udi" string="/org/freedesktop/Hal/devices/macbook_lcd_panel">
      <append key="info.capabilities" type="strlist">laptop_panel</append>
      <merge key="info.product" type="string">MacBook Laptop Panel</merge>
      <merge key="laptop_panel.access_method" type="string">macbook</merge>
      <merge key="laptop_panel.num_levels" type="int">148</merge>
    </match>
  <device>


hal-system-lcd-get-brightness-linux: (line 65)
elif [ "$HAL_PROP_LAPTOP_PANEL_ACCESS_METHOD" = "macbook" ]; then
	value="`/usr/bin/macbook-backlight $value`"
	RETVAL=$?
	if [ $RETVAL != 0 ]; then
		echo "org.freedesktop.Hal.Device.LaptopPanel.NotSupported" >&2
		exit 1;
	fi
	exit ${value}


hal-system-lcd-set-brightness-linux: (line 60)
elif [ "$HAL_PROP_LAPTOP_PANEL_ACCESS_METHOD" = "macbook" ]; then
	value="`/usr/bin/macbook-backlight $value`"
	RETVAL=$?
	if [ $RETVAL != 0 ]; then
		echo "org.freedesktop.Hal.Device.LaptopPanel.NotSupported" >&2
		exit 1;
	fi
	exit ${value}


i use macbook-backlight C code from
http://desrt.mcmaster.ca/code/macbook-backlight/macbook-backlight.c

hal now recognize the device but i can't get value or correctly set the device
and i'm a bit lost to undestand why

Best Regards
Eloi Primaux
Comment 1 Danny Kukawka 2007-04-02 03:30:57 UTC
HAL has now support for Macbook Pro and Macbook laptop panels. Try hal >= 0.5.9rc3.
Comment 2 Eloi Primaux 2007-04-04 00:53:28 UTC
(In reply to comment #1)
> HAL has now support for Macbook Pro and Macbook laptop panels. Try hal >=
> 0.5.9rc3.
> 

Well there is a strange bug, (with both 0.5.9rc3 an 0.5.9)
it correctly set the backlight device but makes the macbook crash at the second suspend:
system starts : backlight correctly set
system suspends: the backlight is at maximum power and macbook-backlight returns
unexpected maximum brightness value
  please email desrt@desrt.ca about this. 
system suspends and crashs

However if i use fixbacklight after the first suspend the backlight function return to its normal state and the system can now correctly suspend without crashing

fixbacklight is a little hack which was done by Ryan Lortie, i think this little c code was commited in x because x now correctly wakeup after a suspend (xorg from git)

i still have the C code here :

//start

/*
 * Macbook Backlight Control
 * Copyright © 2006 Ryan Lortie <desrt@desrt.ca>
 * 
 * HAL integration Copyright © 2007 Ryan Lortie <desrt@desrt.ca>
 * using code Copyright © 2006 David Zeuthen <david@fubar.dk>
 *
 *   This program is free software; you can redistribute it and/or modify
 *   it under the terms of version 2 of the GNU General Public License as
 *   published by the Free Software Foundation.
 *
 *   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  02110 USA
 *
 * This program was written after I reverse engineered the
 * AppleIntelIntegratedFramebuffer.kext kernel extension in Mac OS X and
 * played with the register at the memory location I found therein.
 *
 * From my experiments, the register appears to have two halves.
 *
 * yyyyyyyyyyyyyyy0xxxxxxxxxxxxxxx0
 *
 * The top (y) bits appear to be the maximum brightness level and the
 * bottom (x) bits are the current brightness level.  0s are always 0.
 * The brightness level is, therefore, x/y.
 *
 * As my Macbook boots, y is set to 0x94 and x is set to 0x1f.  Going below
 * 0x1f produces odd results.  For example, if you come from above, the
 * backlight will completely turn off at 0x12 (18).  Coming from below,
 * however, you need to get to 0x15 (21) before the backlight comes back on.
 *
 * Since there is no clear cut boundry, I assume that this value specifies
 * a raw voltage.  Also, it appears that the bootup value of 0x1f corresponds
 * to the lowest level that Mac OS X will set the backlight I choose this
 * value as a minimum.
 *
 * For the maximum I do not let the value exceed the value in the upper 15
 * bits.
 *
 * Turning the backlight off entirely is not supported (as this is supported
 * by the kernel itself).  This utility is only for setting the brightness
 * of the backlight when it is enabled.
 */

#include <pci/pci.h>

#include <stdio.h>
#include <sys/mman.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>

enum { FALSE, TRUE };

#define REGISTER_OFFSET       0x00061254
#define PAGE_SIZE             4096
#define PAGE_MASK             (PAGE_SIZE - 1)

#define ACCESS_OFFSET         (REGISTER_OFFSET & PAGE_MASK)
#define ACCESS_INDEX          (ACCESS_OFFSET >> 2)

unsigned int *register_page;

static unsigned long
determine_video_base_address (void)
{
  struct pci_access *pacc;
  struct pci_dev *pdev;
  unsigned long address;
  int i;

  address = 0;

  pacc = pci_alloc ();
  pci_init (pacc);
  pci_scan_bus (pacc);

  for (pdev = pacc->devices; pdev; pdev = pdev->next)
  {
    pci_fill_info (pdev, PCI_FILL_IDENT | PCI_FILL_BASES);

    if (pdev->vendor_id == 0x8086 && pdev->device_id == 0x27a2)
      for (i = 0; i < 6; i++)
      {
        if (pdev->size[i] == 512 * 1024)
        {
          address = pdev->base_addr[i];
          goto end;
        }
      }
  }

end:
  pci_cleanup (pacc);

  return address;
}

static unsigned long
register_get (void)
{
  return register_page[ACCESS_INDEX];
}

static void
register_set (unsigned long value)
{
  register_page[ACCESS_INDEX] = value;
}


static int
map_register_page (void)
{
  long address;
  int fd;

  address = determine_video_base_address ();

  if (address == 0)
    return FALSE;
  
  fd = open ("/dev/mem", O_RDWR);

  if (fd < 0)
    return FALSE;

  register_page = mmap (NULL, PAGE_SIZE, PROT_READ | PROT_WRITE,
                        MAP_SHARED, fd,
                        (address + REGISTER_OFFSET) & ~PAGE_MASK);

  close (fd);

  if (register_page == MAP_FAILED)
    return FALSE;

  return TRUE;
}

int
main (void)
{
  if (!map_register_page ())
    fprintf (stderr, "cannot map register page!\n");
  else
    register_set ((0x94 << 17) | (0x94 << 1));

  return 0;
}

//end

Comment 3 chemtech 2013-03-26 08:01:51 UTC
Eloi Primaux,
Do you still experience this issue with newer soft ?
Please check the status of your issue.
Or close this bug.

Use of freedesktop.org services, including Bugzilla, is subject to our Code of Conduct. How we collect and use information is described in our Privacy Policy.