Difference between pages "Bluetooth made easy" and "Googleearth panaramio fix"

(Difference between pages)
m (added rfkill 1-liner, minor edits, format changes)
 
(original creation of googleearth panaramio fix)
 
Line 1: Line 1:
== Kernel Support ==
+
== Introduction ==
You must have bluetooth support in your kernel if you are going to use bluetooth. Enable the following in your kernel config:
+
Since version 7.x of GoogleEarth the panaramio function has been broken.  This is not Funtoo specific, all Linux distributions suffer from it.  It is caused by the bundled qt-libs.  This can be repaired by forcing GoogleEarth to use the native Funtoo qt-libraries.
 +
 
 +
== Prerequisites ==
 +
You need the following up to date packages installed on your system:
 +
* '''media-libs/freeimage'''
 +
* '''dev-qt/qtcore'''
 +
* '''dev-qt/qtgui'''
 +
* '''dev-qt/qtwebkit'''
 +
 
 +
== Procedure ==
 +
1.  If not already installed, install GoogleEarth:
 +
 
 +
 
 
<console>
 
<console>
##i##Networking support →
+
##i##echo "=sci-geosciences/googleearth-7.(current version)">>/etc/portage/package.unmask
  ##i##Bluetooth subsystem support →
+
##i##echo "=sci-geosciences/googleearth-7.(current version)">>/etc/portage/package.accept_keywords
  <m> RFCOMM protocol support
+
##i##echo ">=sci-geosciences/googleearth-7.(current version) googleearth">>/etc/portage/package.license
    <y> RFCOMM tty support
+
##i##emerge -av sci-geosciences/googleearth
  <m> BNEP protocol support
+
    <y> Multicast filter support
+
    <y> Protocol filter support
+
  <m> HIDP protocol support
+
 
</console>
 
</console>
I find no difference in choosing built-in modules vs. loading modules with the exception that someday you may wish to use out-of-tree drivers directly from wireless.kernel.org.  Just adding all the modules guarantees you can do anything bluetooth in the future, not worth worrying about saving a tiny bit of space.
 
  
Also be sure and select your bluetooth device driver:
+
 
 +
2.  In GoogleEarth's running directory /opt/googleearth, remove the 4 original libQt* libraries and save them in a new directory:
 +
 
 +
 
 
<console>
 
<console>
##i##Networking support →
+
##i##cd /opt/googleearth
##i## Bluetooth subsystem support →
+
##i##mkdir bundled-qtlib
##i##   Bluetooth device drivers →
+
##i##mv libQt* bundled-qtlib/
        <m> HCI USB driver
+
 
</console>
 
</console>
Make sure you choose at least the HCI USB driver.  Others may be applicable to your setup too, for example, if you have a Broadcom BCM203x device you'll want the driver for that which loads the appropriate firmware.
+
 
== Userspace Programs ==
+
 
As of this writing there have been big changes in bluez.  If you intend to use headsets, they (currently) will NOT work with bluez-5.x. The HSP/HFP protocol that these headsets use were set up by bluez (in the past), but that now will be handled by pulseaudio (in the future).  For headset owners (in the present) you must choose bluez-4.x and pulseaudio-4.x if you intend to use them.  So mask the newer versions in /etc/portage/package.mask:
+
3.  If you invoke googleearth now, you will get the known error:
 +
    ./googleearth-bin: symbol lookup error: ./libbase.so: undefined symbol: _Z34QBasicAtomicInt_fetchAndAddOrderedPVii
 +
    The missing function can be generated by creating a file in /opt/googleearth (call it baifaao.cpp) with this content:
 +
 
 +
 
 
<console>
 
<console>
echo “>bluez-4.(whatever version you choose)”>>/etc/portage/package.mask
+
##i##/* /opt/googleearth/baifaao.cpp */
echo “>pulseaudio-4.(whatever version you choose)”>>/etc/portage/package.mask
+
##i###include <QtCore/QAtomicInt>
 +
##i##extern "C" {
 +
##i## int _Z34QBasicAtomicInt_fetchAndAddOrderedPVii(QAtomicInt* a, int b) {
 +
##i## return a->fetchAndAddOrdered(b);
 +
##i## }
 +
##i##}
 
</console>
 
</console>
A2DP and other protocols still work fine in bluez-5, so if you don't intend to use headsets the above doesn't apply.
 
  
Add “bluetooth” to your USE flags in /etc/portage/make.conf
 
  
And then: emerge -aND @world
+
4.  Compile it and create the shim library with the following command line:
  
If you need firmware for your bluetooth receiver be sure and get that too.  Sys-kernel/linux-firmware is always a safe bet to have on hand.
 
  
You'll want to add bluetooth to your startup:
 
 
<console>
 
<console>
# rc-update add bluetooth default
+
##i##gcc -I/usr/include/qt4 -O3 -fPIC --shared baifaao.cpp -o baifaao.so
 
</console>
 
</console>
== Usage ==
 
While it's rumored that some high-profile Funtoo users refuse to even run X server, for the rest of us a handy GUI can be nice.  However, be aware that all operations can be done from the command line as well.  If you intend to do that, bluez-4.x needs to be installed with the “test-programs” USE flag.  I don't believe it's necessary with bluez-5 and above.
 
  
For bluez-4.x/pulseaudio-4.x users wanting a GUI you can use gnome-bluetooth (I recommend <=3.6) or blueman.  The blueman project has been abandoned, but still works fine until we all move on past version 4 bluez.
 
  
For bluez-5.x users the choice is more limitedBlueman will not work.  A newer version of gnome-bluetooth probably does, not tested here.  I did test bluedevil and it seemed to work, but I suspect initial pairing must still be done at the command line.
+
5.  In the file googleearth (in the directory /opt/googleearth), add the following line, e.g. before the line starting with LD_LIBRARY_PATH:
  
Pair up your devices, you're ready to go!  For bluez-4.x with GUI this is pretty trivial, if you have issues, there is plenty on the web.  Bluez-5.x is a little different, as far as I have seen it is all done at the command line, once again I refer you to the web where it is covered in detail.
 
  
== Custom Tips ==
 
{{fancynote|Some of the following requires installation of net-wireless/rfkill, a handy thing to have anyway}}
 
With bluez-5.x, things are bit strange.  It starts with your bluetooth device (receiver) powered off.  For those that would like their bluetooth active on machine start, the following code passing around the web added to /etc/udev/rules.d/10-local.rules is purported to work:
 
 
<console>
 
<console>
##i###/etc/udev/rules.d/10-local.rules
+
##i##export LD_PRELOAD=/usr/lib64/libfreeimage.so.3:/opt/googleearth/baifaao.so
##i### Set bluetooth power up
+
##i##ACTION=="add", KERNEL=="hci0", RUN+="/usr/bin/hciconfig hci0 up"
+
 
</console>
 
</console>
However, I suspect the same technique the author has been using for years will work just as well.  At any rate, while bluez-4.x powers your device on at startup, by the same token you can start it powered down and then use a hotkey to toggle it.  By adding the following to your /etc/local.d/*.start file:
+
 
 +
 
 +
 
 +
x86 32 bit users should use:  
 +
 
 +
 
 +
 
 
<console>
 
<console>
##i###/etc/local.d/*.start
+
##i##export LD_PRELOAD=/usr/lib/libfreeimage.so.3:/opt/googleearth/baifaao.so
##i##rfkill block bluetooth
+
 
</console>
 
</console>
Bluez-4.x will start with the device powered off.
 
  
Or, you bluez-5.x users that want your device powered on start:
+
 
 +
 
 +
6.  If the locale bug in the QT libs is not patched it may cause a major coordinate shift if the locale is not en_US.UTF-8.  
 +
    If it is still present with your locale, add also:
 +
 
 +
 
 
<console>
 
<console>
##i###/etc/local.d/*.start
+
##i##export LC_NUMERIC=en_US.UTF-8
##i##rfkill unblock bluetooth  #UNTESTED!
+
 
</console>
 
</console>
/etc/local.d/*.start operates as the root user.  This is convenient, as rfkill requires root to execute.
 
  
Your bluetooth device will be physically powered down (no electricity even) when rfkill blocks it.  Most desktop environments, Gnome, KDE, etc. have some way to assign a hotkey to a command.  However, these commands are limited to the unprivileged user.  Since rfkill must be run by root I use the following method.
 
  
First, we need toggle action, so one hotkey can turn bluetooth either off or onThe following code accomplishes that.
+
  7At least at this location, panaramio and much of GoogleEarth works only with qtgraphicssystem=native.
I have a /home/<username>/bin directory with many “helper” programsIn there, create a file owned by root, with chmod 744 permissions called bluetooth.
+
    There are a few ways to do thisOne is to permanently choose it:
 +
 
 +
 
 
<console>
 
<console>
##i##$ cd ~
+
##i##eselect qtgraphicssystem set native
##i##$ mkdir bin
+
##i##$ cd bin
+
##i##$ touch bluetooth
+
##i##$ sudo chown root: bluetooth
+
##i##$ sudo chmod 744 bluetooth
+
 
</console>
 
</console>
Paste the following code into the file with your favorite editor, taking care to change the device name as noted.
 
<pre>
 
#/home/<username>/bin/bluetooth
 
#keyboard shortcut set to <your choice>, toggles bluetooth on & off
 
#this file must be added to sudoers ;)
 
  
# we need to find which rfkill applies to bluetooth, there can be one for wifi, one for bluetooth, I have a 3rd , don't even know what it is
 
  
for file in /sys/class/rfkill/*
+
Or if you choose to primarily run another setting with qtgraphicssystem you can use the following approach:
do
+
 
if [ "$(cat ${file}/name)" = "hp-bluetooth" ]; then  ### you'll have to snoop around in there, rename to what your device is called
+
 
BT_STATE=$(cat ${file}/state)
+
fi
+
done
+
if [[ ${BT_STATE} -eq 1 ]]; then
+
rfkill block bluetooth
+
BLUETOOTH_STRING="  Bluetooth powered off"
+
DISPLAY_COLOR="red"
+
else
+
        rfkill unblock bluetooth
+
BLUETOOTH_STRING="  Bluetooth powered on"
+
DISPLAY_COLOR="blue"
+
fi
+
# Clean up any running aosd_cat processes
+
killall aosd_cat &> /dev/null
+
# Display the desired text
+
echo "$BLUETOOTH_STRING" | aosd_cat -n "Georgia Italic 120" -u 1000 -o 200 -R $DISPLAY_COLOR -S black -f 0 -e 4 -p 3 -x 300
+
</pre>
+
As you can see, I also have a display that prints huge colored letters across my screen telling bluetooth status for a few seconds as I enable/disable it.  To have the display you must install x11-libs/libaosd.  That's it, the code in the bluetooth program shows how to use this handy library, you can tweak font size, etc. to your liking.
+
  
This one-liner will list out the available rfkill named devices on your computer:
 
 
<console>
 
<console>
for file in /sys/class/rfkill/* ; do echo "$(cat ${file}/name)"; done
+
##i##cp /usr/share/applications/google-earth.desktop /home/<username>/.local/share/applications
 +
##i##cd /home/<username>/.local/share/applications
 +
##i##chown <username>: google-earth.desktop
 
</console>
 
</console>
You may have to snoop around a bit in /sys to find what you're looking for.  The name of your device may be something as simple as hci0.  I actually use /sys/devices/platform/hp-wmi/rfkill/* on my system, but this generic method should work for you.  A static directory usually doesn't work, it's often different on every startup, hence the search code.
 
  
Since this program is owned by root, and in fact, rfkill itself must be run as root, simply put the following line in your sudoers file:
+
 
<console>
+
Now edit google-earth.desktop with your favorite editor, changing the line beginning with "Exec" as follows:
##i##<username> ALL = NOPASSWD: /home/<username>/bin/bluetooth
+
 
</console>
+
 
Now just add the following command to your hotkey assignment, and you can toggle bluetooth on & off to your heart's content:
+
 
<console>
 
<console>
##i##sudo /home/<username>/bin/bluetooth
+
##i### old line:
 +
##i###Exec=/opt/googleearth/googleearth %f
 +
##i### new line:
 +
##i##Exec=env QT_GRAPHICSSYSTEM=native /opt/googleearth/googleearth %f
 
</console>
 
</console>
== Yet Another Trick ==
 
Another handy thing that can be done.  I have 2 computers at my desk, 1 is rarely used and somewhat underpowered.  I sometimes use it though to talk on voip, leaving my main machine free to compile, restart, whatever.
 
  
The problem: I wish to use the same headsets on both computers.  In practice, this is a bit of a hassle, because you must pair the headsets with only one machine, so as I switch back and forth, I have to change the pairing.  Not the end of the world, but we can end that hassle.
 
  
{{fancynote|Some newer headsets can be paired to as many as 3 different receivers, great if you have them}}
+
  Or I find this works well on nvidia:
The first task is to acquire the bdaddr program. It's on the Backtrack Linux distros, you can probably find it out there in cyberspace somewhere, but it gets confusing on a search because bluez uses the bdaddr abbreviation a lot, creating a lot of noise in your search.
+
I just put it in /usr/bin.
+
  
To accomplish this, one machine must be the “Master Record” and the other machine pretends to be that machine with pairing.  Not as complicated as it sounds.
 
  
Now pair all of your devices on the “Master Record” machine.  The secret link codes are stored at (shhhh!) /var/lib/bluetooth in a directory named with your receivers bluetooth address, let's say AA:AA:AA:AA:AA:AA.  After this is done you are ready to start on the Pretender machine.  It will fool bluez into thinking that it's bluetooth address is AA:AA:AA:AA:AA:AA, even though it has a different address.  Copy the  AA:AA:AA:AA:AA:AA directory from /var/lib/bluetooth on the “Master Record” machine to /var/lib/bluetooth on the “Pretender”.  The Pretender will now have two directories in /var/lib/bluetooth,  AA:AA:AA:AA:AA:AA and it's own receiver's address directory.  (Unless you have more than 1 receiver, but let's keep it simple).
 
 
Then simply modify the code in /home/<username>/bin/bluetooth, only the “turn on” section is shown below, because that's all we are changing:
 
 
<console>
 
<console>
#/home/<username>/bin/bluetooth (partial)
+
##i##Exec=env XLIB_SKIP_ARGB_VISUALS=1 QT_GRAPHICSSYSTEM=native /opt/googleearth/googleearth %f
...  else
+
      rfkill unblock bluetooth
+
##i### add these 4 lines
+
##i##        sleep 2
+
##i##        /usr/bin/bdaddr -i hci0 AA:AA:AA:AA:AA:AA  2&>1>/dev/null #of course, you must change this to "Master Record's" receiver address
+
##i##        /usr/sbin/hciconfig hci0 reset
+
##i##        /etc/init.d/bluetooth restart
+
##i### end of addition
+
BLUETOOTH_STRING="  Bluetooth powered on"
+
DISPLAY_COLOR="blue"  ...
+
 
</console>
 
</console>
And that's it!  Now both machines will use the same headsets and you won't constantly have to re-pair.  When the Pretender bluetooth is toggled on it has the other machines bluetooth address for it's receiver.  Note that I always start my bluetooth powered off, so it always starts in pretend mode, if you start with yours powered on it won't spoof the other address until you toggle it off & then on unless you add the above code to your /etc/local.d/*.start file as well.
 
  
The only caveat is I'm not sure what would ever happen if I had both bluetooth receivers on at the same time and turned on a headset.  But far short of a nuclear meltdown I'm sure, I suspect one machine would grab the headset before the other?  Anyhow, with hotkey controlled bluetooth it's never been an issue.
+
 
 +
Whew!  Take a breather and enjoy some of those photos from exotic locales :)
 +
 
 +
 
 +
    Much of the content of this page is a derivative of comments on a Gentoo bug on this specific subject.
 +
    It can be found at: https://bugs.gentoo.org/show_bug.cgi?id=490066

Revision as of 01:39, April 8, 2014

Introduction

Since version 7.x of GoogleEarth the panaramio function has been broken. This is not Funtoo specific, all Linux distributions suffer from it. It is caused by the bundled qt-libs. This can be repaired by forcing GoogleEarth to use the native Funtoo qt-libraries.

Prerequisites

You need the following up to date packages installed on your system:

  • media-libs/freeimage
  • dev-qt/qtcore
  • dev-qt/qtgui
  • dev-qt/qtwebkit

Procedure

1.  If not already installed, install GoogleEarth:


echo "=sci-geosciences/googleearth-7.(current version)">>/etc/portage/package.unmask
echo "=sci-geosciences/googleearth-7.(current version)">>/etc/portage/package.accept_keywords
echo ">=sci-geosciences/googleearth-7.(current version) googleearth">>/etc/portage/package.license
emerge -av sci-geosciences/googleearth


2.  In GoogleEarth's running directory /opt/googleearth, remove the 4 original libQt* libraries and save them in a new directory:


cd /opt/googleearth
mkdir bundled-qtlib
mv libQt* bundled-qtlib/


3.  If you invoke googleearth now, you will get the known error:
    ./googleearth-bin: symbol lookup error: ./libbase.so: undefined symbol: _Z34QBasicAtomicInt_fetchAndAddOrderedPVii
    The missing function can be generated by creating a file in /opt/googleearth (call it baifaao.cpp) with this content:


/* /opt/googleearth/baifaao.cpp */
#include <QtCore/QAtomicInt>
extern "C" {
	int _Z34QBasicAtomicInt_fetchAndAddOrderedPVii(QAtomicInt* a, int b) {
		return a->fetchAndAddOrdered(b);
	}
}


4.  Compile it and create the shim library with the following command line:


gcc -I/usr/include/qt4 -O3 -fPIC --shared baifaao.cpp -o baifaao.so


5.  In the file googleearth (in the directory /opt/googleearth), add the following line, e.g. before the line starting with LD_LIBRARY_PATH:


export LD_PRELOAD=/usr/lib64/libfreeimage.so.3:/opt/googleearth/baifaao.so


x86 32 bit users should use:


export LD_PRELOAD=/usr/lib/libfreeimage.so.3:/opt/googleearth/baifaao.so


6.  If the locale bug in the QT libs is not patched it may cause a major coordinate shift if the locale is not en_US.UTF-8. 
    If it is still present with your locale, add also:


export LC_NUMERIC=en_US.UTF-8


7.  At least at this location, panaramio and much of GoogleEarth works only with qtgraphicssystem=native.  
    There are a few ways to do this.  One is to permanently choose it:


eselect qtgraphicssystem set native


Or if you choose to primarily run another setting with qtgraphicssystem you can use the following approach:


cp /usr/share/applications/google-earth.desktop /home/<username>/.local/share/applications
cd /home/<username>/.local/share/applications
chown <username>: google-earth.desktop


Now edit google-earth.desktop with your favorite editor, changing the line beginning with "Exec" as follows:


# old line:
#Exec=/opt/googleearth/googleearth %f
# new line:
Exec=env QT_GRAPHICSSYSTEM=native /opt/googleearth/googleearth %f


Or I find this works well on nvidia:


Exec=env XLIB_SKIP_ARGB_VISUALS=1 QT_GRAPHICSSYSTEM=native /opt/googleearth/googleearth %f


Whew! Take a breather and enjoy some of those photos from exotic locales :)


   Much of the content of this page is a derivative of comments on a Gentoo bug on this specific subject.
   It can be found at: https://bugs.gentoo.org/show_bug.cgi?id=490066