Wednesday, June 10, 2015

i3: Launch Android Studio on specific workspace

i3 supports launching specific applications on specific workspace. The problem with Android Studio is that it displays a splash screen and loads the full program, matching applications by title doesn't work in this case.

However, WM_CLASS comes to rescue. Android Studio's WM_CLASS is set to "jetbrains-studio" and we can match that. (This was gathered using xprop.)

Just add the following lines to the end of i3 config file at ~/.i3/config

assign [class="jetbrains-studio"]  2

This makes Android Studio launch by default on Workspace "2".

Tested for : Android Studio 1.2

Sunday, June 7, 2015

Install Debian with Network Install ISO and Grub

What if you want to test an ISO without asking your VPS Provider to put the ISO in their control panel? This is one of the case where directly booting off an ISO image is a better option.

So, let's assume we want to install Debian 8 (amd64) from network. First the server(or perhaps desktop) should have any kind of Linux preinstalled. I am assuming you have a flavor of Linux that is powered by "apt".

Step 1: Install Grub and grub-imageboot

Grub supports booting from ISO images. And, grub-rescueboot makes life easier. Issue the following commands as root:
# apt-get install grub2 grub-imageboot
This will create a new folder on /boot/images where you can put any ISO files and it will be on the meny entry of Grub.

Step 2: Download ISO Image

URL in command below points to minimal CD image (around ~21MB) that can be used to boot latest Debian installer.

# mkdir /boot/images
# wget -P /boot/images http://ftp.debian.org/debian/dists/stable/main/installer-amd64/current/images/netboot/mini.iso

This will download the ISO to /boot/images .

Step 3: Update Grub entry

# update-grub

Step 4: Restart

Now, restart your server and select the Grub entry. If you are doing this on a remote server or VPS, use VNC, it's available in most of the control panels.

grml-rescueboot is an alternative similar to grub-imageboot but it didn't work for me.

Saturday, November 22, 2014

Undefined References to Boost Libraries - Solution

Yesterday, I was trying to compile a C++ source that uses Gnuplot-iostream interface. I issued the following compilation command:
$ g++ -std=c++11 -lboost_iostreams -lboost_system -lboost_filesystem ProcessScheduler.cpp 
/tmp/cchNNC8H.o: In function `__static_initialization_and_destruction_0(int, int)':
ProcessScheduler.cpp:(.text+0xc52): undefined reference to `boost::system::generic_category()'
ProcessScheduler.cpp:(.text+0xc5e): undefined reference to `boost::system::generic_category()'
ProcessScheduler.cpp:(.text+0xc6a): undefined reference to `boost::system::system_category()'
collect2: error: ld returned 1 exit status
I even had libboost-system-dev, libboost-filesystem-dev and libboost-iostreams-dev installed.
After searching for over an hour, I found that the problem was with how new g++ treated the command-line options.

The solution was to change the position of arguments.
$ g++ -std=c++11  ProcessScheduler.cpp  -lboost_iostreams -lboost_system -lboost_filesystem
So, adding linker parameters after source file worked.
The page at Link Options - GCC states that:
-l library [...] It makes a difference where in the command you write this option; the linker searches and processes libraries and object files in the order they are specified. Thus, ‘foo.o -lz bar.o’ searches library ‘z’ after file foo.o but before bar.o. If bar.o refers to functions in ‘z’, those functions may not be loaded. [...]

Saturday, June 28, 2014

Streaming USB webcam on Raspberry PI

I had a USB webcam lying around and a Raspberry Pi. And, I wanted to stream it over my local WiFi network. To do this, I picked up MJPEG-Streamer. Connecting the webcam and issuing 'lsmod' showed this:
$ lsmod
.
.
Bus 001 Device 004: ID 0ac8:3420 Z-Star Microelectronics Corp. Venus USB2.0 Camera
The device is supported by UVC driver.
ls /dev/vid*
/dev/video0
So, we have '/dev/video0' as our webcam.
Let's install some required packages.
On a RPi, I have faced multiple issues trying to install packages without first upgrading the system to the latest state. So, let's upgrade the system first.
$ sudo apt-get update && sudo apt-get upgrade
And, some requirements for MJPEG-Streamer
$ sudo apt-get install subversion imagemagick libjpeg8-dev
Now, let's download the latest source
$ svn co https://svn.code.sf.net/p/mjpg-streamer/code/mjpg-streamer/ mjpg-streamer
$ make
When it finishes, it leaves "mjpeg-streamer" binary to the folder. This may be added to path variable. Now, let's stream. 15fps with hardware MJPEG Compression
$ ./mjpg_streamer -i "./input_uvc.so -d /dev/video0 -f 15 " -o "./output_http.so -w ./www"
If you get the error like this:
The input device does not supports MJPEG mode
You may also try the YUV mode (-yuv option), but it requires a much more CPU power
 Init v4L2 failed !! exit fatal 
 i: init_VideoIn failed
Then we need to add '-y' argument to fallback to software mode.
$ ./mjpg_streamer -i "./input_uvc.so -d /dev/video0 -y -f 15" -o "./output_http.so -w ./www"
You can access the web interface at http://<ip>:8080/ where 'ip' is the IP of the Raspberry Pi server. The frame rate can also be changed by specifying the custom value instead of 15. To stream at different resolution with 30fps:
$ ./mjpg_streamer -i "./input_uvc.so -d /dev/video0 -f 15 -r 960x720" -o "./output_http.so -w ./www"
The best part of MJPEG-Streamer is that you can also use VLC or any other streaming player to watch the stream and you are not limited to a web interface.
Happy streaming.