<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>blog &#124; edwards research</title>
	<atom:link href="http://blog.edwards-research.com/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.edwards-research.com</link>
	<description>some notes from our staff...</description>
	<lastBuildDate>Tue, 01 May 2012 21:24:44 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.1.2</generator>
		<item>
		<title>Tutorial: Android JNI (Part&#160;2)</title>
		<link>http://blog.edwards-research.com/2012/05/tutorial-android-jni-part-2/</link>
		<comments>http://blog.edwards-research.com/2012/05/tutorial-android-jni-part-2/#comments</comments>
		<pubDate>Tue, 01 May 2012 21:21:43 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[android]]></category>
		<category><![CDATA[c]]></category>
		<category><![CDATA[java]]></category>
		<category><![CDATA[uncategorized]]></category>
		<category><![CDATA[jni]]></category>
		<category><![CDATA[native interface]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=655</guid>
		<description><![CDATA[This is continued from Part 1. In the first part, we setup the project structure, wrote the java wrapper class, generated the c header, wrote the c library and write the Android.mk file. Building shared library With traditional JNI (not targetting Android devices), you just compile the library with gcc using the -shared option. However, [...]]]></description>
			<content:encoded><![CDATA[<p>This is continued from <a href="http://blog.edwards-research.com/2012/04/tutorial-android-jni/">Part 1</a>.</p>
<p>In the first part, we setup the project structure, wrote the java wrapper class, generated the c header, wrote the c library and write the <span class="pre">Android.mk</span> file.</p>
<p>
<h2>Building shared library</h2>
<p>With traditional JNI (not targetting Android devices), you just compile the library with <span class="pre">gcc</span> using the <span class="pre">-shared</span> option.  However, for Android devices, we use the <span class="pre">ndk-build</span> script.</p>
<p>To compile, we first switch to the project directory (the directory that contains the <span class="pre">jni</span> and <span class="pre">src</span> directories then run the ndk-build script provided in the Android NDK:</p>
<pre class="brush: bash; title: ; notranslate">
cd Android-JNI-Demo
/path/to/ndk-build # for example: ~/build/android-ndk/android-ndk-r7c/ndk-build
</pre>
<p>If when trying to compile on linux you get the following error:</p>
<pre>
Invalid attribute name:
    package
</pre>
<p>You&#8217;ll want to check the line endings of your <span class="pre">AndroidManifest.xml</span>.  I used the <span class="pre">dos2unix</span> command to correct them.</p>
<p>If the build script found your <span class="pre">Android.mk</span> and the library compiled without issue, you&#8217;ll see the following:</p>
<pre>
Compile thumb  : squared <= squared.c
SharedLibrary  : libsquared.so
Install        : libsquared.so => libs/armeabi/libsquared.so
</pre>
<p>So we&#8217;re happy with the library compilation and now we&#8217;ll move on the developing a simple UI to test whether our functions perform as we expect.</p>
<p>
<h2>Develop Simple UI</h2>
<p>By default, when we created a new Android project in Eclipse an activity was generated with the following:</p>
<pre class="brush: java; title: ; notranslate">
package org.edwards_research.demo.jni;

import android.app.Activity;
import android.os.Bundle;

public class Android_JNI_DemoActivity extends Activity {
    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
    }
}
</pre>
<p>If we didn&#8217;t care about looking pretty, we could change this to something like:</p>
<pre class="brush: java; title: ; notranslate">
package org.edwards_research.demo.jni;

import android.app.Activity;
import android.os.Bundle;
import android.util.Log;

public class Android_JNI_DemoActivity extends Activity {
    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        int b = 3;
        int a = SquaredWrapper.to4(b);
        Log.i(&quot;JNIDemo&quot;, String.format(&quot;%d-&gt;%d&quot;, b,a));
    }
}
</pre>
<p>and run it, either in the emulator or on a device (with USB debugging enabled), we would see in LogCat an entry tagged with <span class="pre">JNIDemo</span>.  In this case, we&#8217;d expect something like <span class="pre">3->81</span>, since 3^4 = 81.  But we&#8217;ll do a little bit more to see the performance of the library directly on the UI.</p>
<p>Instead of walking through the specific steps of creating the UI, I&#8217;ll simply post the pertinent files:</p>
<p><strong><span class="pre">Android_JNI_DemoActivity.java</pre>
<p></strong></p>
<pre class="brush: java; title: ; notranslate">
package org.edwards_research.demo.jni;

import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.EditText;
import android.widget.TextView;

public class Android_JNI_DemoActivity extends Activity {
    private EditText etInput;
    private TextView txtTo2;
    private TextView txtTo4;

    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        // Define Input EditText, TextViews
        etInput = (EditText) findViewById(R.id.etInput);
        txtTo2 =  (TextView) findViewById(R.id.resTo2);
        txtTo4 =  (TextView) findViewById(R.id.resTo4);
    }

    public void cbCalculate(View view)
    {
        int in = 0;
        try{
            in = Integer.valueOf( etInput.getText().toString() );
        } catch(NumberFormatException e) { return ; }

        txtTo2.setText(String.format(&quot;%d&quot;, SquaredWrapper.squared(in)));
        txtTo4.setText(String.format(&quot;%d&quot;, SquaredWrapper.to4(in)));
    }
}
</pre>
<p><strong><span class="pre">res/layout/main.xml</pre>
<p></strong></p>
<pre class="brush: xml; title: ; notranslate">
&lt;?xml version=&quot;1.0&quot; encoding=&quot;utf-8&quot;?&gt;
&lt;LinearLayout xmlns:android=&quot;http://schemas.android.com/apk/res/android&quot;
    android:layout_width=&quot;fill_parent&quot;
    android:layout_height=&quot;fill_parent&quot;
    android:orientation=&quot;vertical&quot; &gt;

    &lt;TableLayout
        android:id=&quot;@+id/tableLayout1&quot;
        android:layout_width=&quot;match_parent&quot;
        android:layout_height=&quot;wrap_content&quot; &gt;

        &lt;TableRow
            android:id=&quot;@+id/tableRow1&quot;
            android:layout_width=&quot;wrap_content&quot;
            android:layout_height=&quot;wrap_content&quot; &gt;

            &lt;EditText
                android:id=&quot;@+id/etInput&quot;
                android:layout_width=&quot;150dp&quot;
                android:layout_height=&quot;wrap_content&quot;
                android:inputType=&quot;number&quot; /&gt;

            &lt;Button
                android:id=&quot;@+id/button1&quot;
                android:layout_width=&quot;wrap_content&quot;
                android:layout_height=&quot;wrap_content&quot;
                android:text=&quot;Calculate&quot;
                android:onClick=&quot;cbCalculate&quot;/&gt;

        &lt;/TableRow&gt;

        &lt;TableRow
            android:id=&quot;@+id/tableRow2&quot;
            android:layout_width=&quot;wrap_content&quot;
            android:layout_height=&quot;wrap_content&quot; &gt;

            &lt;TextView
                android:id=&quot;@+id/lblTo2&quot;
                android:layout_width=&quot;match_parent&quot;
                android:layout_height=&quot;wrap_content&quot;
                android:text=&quot;@string/squared&quot; /&gt;

            &lt;TextView
                android:id=&quot;@+id/resTo2&quot;
                android:layout_width=&quot;wrap_content&quot;
                android:layout_height=&quot;wrap_content&quot;
                android:text=&quot;&quot; /&gt;

        &lt;/TableRow&gt;

        &lt;TableRow
            android:id=&quot;@+id/tableRow3&quot;
            android:layout_width=&quot;wrap_content&quot;
            android:layout_height=&quot;wrap_content&quot; &gt;

            &lt;TextView
                android:id=&quot;@+id/lblTo4&quot;
                android:layout_width=&quot;wrap_content&quot;
                android:layout_height=&quot;wrap_content&quot;
                android:text=&quot;@string/to4&quot; /&gt;

            &lt;TextView
                android:id=&quot;@+id/resTo4&quot;
                android:layout_width=&quot;wrap_content&quot;
                android:layout_height=&quot;wrap_content&quot;
                android:text=&quot;&quot; /&gt;

        &lt;/TableRow&gt;

        &lt;TableRow
            android:id=&quot;@+id/tableRow4&quot;
            android:layout_width=&quot;wrap_content&quot;
            android:layout_height=&quot;wrap_content&quot; &gt;
        &lt;/TableRow&gt;
    &lt;/TableLayout&gt;

&lt;/LinearLayout&gt;
</pre>
<p><strong><span class="pre">res/values/strings.xml</pre>
<p></strong></p>
<pre class="brush: xml; title: ; notranslate">
&lt;?xml version=&quot;1.0&quot; encoding=&quot;utf-8&quot;?&gt;
&lt;resources&gt;
    &lt;string name=&quot;app_name&quot;&gt;Android-JNI-Demo&lt;/string&gt;
    &lt;string name=&quot;squared&quot;&gt;Squared:&lt;/string&gt;
    &lt;string name=&quot;to4&quot;&gt;To 4:&lt;/string&gt;
&lt;/resources&gt;
</pre>
<p>When run in the emulator the app looks as follows:<br />
<a href="http://blog.edwards-research.com/wp-content/uploads/2012/05/ER-JNI-UI-1.png" rel="lightbox[655]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/05/ER-JNI-UI-1.png" alt="" title="ER-JNI-UI-1" width="494" height="278" class="aligncenter size-full wp-image-661" /></a></p>
<p>You can enter a number in the text field and press the calculate button which will result in the squared and ^4 calculations:<br />
<a href="http://blog.edwards-research.com/wp-content/uploads/2012/05/ER-JNI-UI-2.png" rel="lightbox[655]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/05/ER-JNI-UI-2.png" alt="" title="ER-JNI-UI-2" width="489" height="271" class="aligncenter size-full wp-image-662" /></a><br />
<a href="http://blog.edwards-research.com/wp-content/uploads/2012/05/ER-JNI-UI-3.png" rel="lightbox[655]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/05/ER-JNI-UI-3.png" alt="" title="ER-JNI-UI-3" width="488" height="293" class="aligncenter size-full wp-image-663" /></a></p>
<p>Of course this was a pretty silly demo library because a squared function could have been trivially implemented in java without the need for c code, cross compiling or dealing at all with the Java Native Interface, however it still illustrated the steps necessary to compile a native library against the Android NDK and how to import and use it in an Android Project.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2012/05/tutorial-android-jni-part-2/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Tutorial: Android&#160;JNI</title>
		<link>http://blog.edwards-research.com/2012/04/tutorial-android-jni/</link>
		<comments>http://blog.edwards-research.com/2012/04/tutorial-android-jni/#comments</comments>
		<pubDate>Tue, 01 May 2012 01:24:04 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[android]]></category>
		<category><![CDATA[c]]></category>
		<category><![CDATA[java]]></category>
		<category><![CDATA[jni]]></category>
		<category><![CDATA[native interface]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=634</guid>
		<description><![CDATA[Today I&#8217;ll be posting a quick walkthrough of how to create and build a simple android project that includes native code using the Java Native Interface (JNI). As a note, there are sample projects included in the Android NDK, but this will walk you through building your own. After going through this, it&#8217;s suggested you [...]]]></description>
			<content:encoded><![CDATA[<p>Today I&#8217;ll be posting a quick walkthrough of how to create and build a simple android project that includes native code using the Java Native Interface (JNI).  As a note, there are sample projects included in the Android NDK, but this will walk you through building your own.  After going through this, it&#8217;s suggested you review these sample projects.</p>
<p>
<h2>Prerequisites</h2>
<p>As a prerequisite for this tutorial, you&#8217;ll need:</p>
<ol>
<li>Eclipse installed and configured to create Android projects.  There are a number of tutorials out there about how to do this if you need help.</li>
<li>A JDK installed, as I don&#8217;t believe the standard JRE contains the <span class="pre">javah</span> command that will be needed.</li>
<li>The Android NDK (<a href="http://developer.android.com/sdk/ndk/index.html">available here</a>) downloaded and extracted somewhere.</li>
</ol>
<p>
<h2>Create the Android Project</h2>
<p>For this tutorial we&#8217;re going to create a new project.  However there is no reason you couldn&#8217;t integrate this into an already-created project.</p>
<p>To create the project, right click in Eclipse&#8217;s Package Explorer &rarr; New &rarr; Android Project.  Give your project a name and select an API.  For this tutorial I choose the latest Gingerbread API, 2.3.3.</p>
<p>
<h2>Add jni folder, <span class="pre">Android.mk</span> makefile</h2>
<p>Once your project has been created, you&#8217;ll need to create a new folder inside the top level of the project.  To do this right click on your project name &rarr; New &rarr; Folder.  Name this folder <span class="pre">jni</span>.</p>
<p>Inside this folder, create a new blank text file.  To do this right click on your newly-created jni folder &rarr; New &rarr; File.  Name this file <span class="pre">Android.mk</span>.  Leave this file blank for now, we&#8217;ll come back to it later.</p>
<p>Your project should look something like this:<br />
<a href="http://blog.edwards-research.com/wp-content/uploads/2012/04/ER-JNI-ProjectLayout.png" rel="lightbox[634]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/04/ER-JNI-ProjectLayout.png" alt="" title="ER-JNI-ProjectLayout" width="295" height="245" class="aligncenter size-full wp-image-640" /></a></p>
<p>
<h2>Create java source</h2>
<p>For this tutorial, we&#8217;re going to have a simple c program &#8212; <span class="pre">squared</span> &#8212; that accepts an int and returns the square (e.g. 2&nbsp;&rarr;&nbsp;4, 3&nbsp;&rarr;&nbsp;9, etc.)</p>
<p>In order to accomodate that, we first create a java source wrapper.  The wrapper&#8217;s job is to load the library, expose any native functions we wish to use directly, and  provide any functions that we want to be able to utilize private native functions.</p>
<p>For this tutorial, we&#8217;re going to expose directly the native <span class="pre">squared</span> function as well as provide a <span class="pre">to4</span> &#8220;derivative&#8221; function.</p>
<p>To expose the native function directly, we just declare it <span class="pre">public</span>.  Alternatively, we could declare it <span class="pre">private</span> and limit it&#8217;s availability to other functions of the class.</p>
<p>Our full java source is</p>
<pre class="brush: java; title: ; notranslate">
package org.edwards_research.demo.jni;

public class SquaredWrapper {
    // Declare native method (and make it public to expose it directly)
    public static native int squared(int base);

    // Provide additional functionality, that &amp;quot;extends&amp;quot; the native method
    public static int to4(int base)
    {
        int sq = squared(base);
        return squared(sq);
    }

    // Load library
    static {
        System.loadLibrary(&amp;quot;squared&amp;quot;);
    }
}
</pre>
<p>
<h2>Create C header</h2>
<p>After we outline the native methods we&#8217;ll be using, we can use this java source to create a c header file with the function prototypes for the native methods we used.  To do this, we first have to compile the java source into a class file.  You can do this manually via the <span class="pre">javac</span> command, e.g.:</p>
<pre class="brush: bash; title: ; notranslate">
cd src # change into the source directory
javac -d /tmp/ org/edwards_research/demo/jni/SquaredWrapper.java
</pre>
<p>Note that the <span class="pre">-d</span> switch specifies the output directory for the class file &#8212; in this case, I&#8217;m just throwing it into <span class="pre">/tmp</span>.</p>
<p>Now that we have the class, we can create the c header file., e.g.:</p>
<pre class="brush: bash; title: ; notranslate">
cd /tmp
javah -jni org.edwards_research.demo.jni.SquaredWrapper
</pre>
<p>Note the need to specify the fullly-qualified class name (including package) and not the <span class="pre">.class</span> file extension.</p>
<p>The resulting header file in our case is <span class="pre">/tmp/org_edwards_research_demo_jni_SquaredWrapper.h</span>, but we can rename it to whatever we want.  In this case, we&#8217;ll rename it to <span class="pre">squared.h</span> and place it in the <span class="pre">jni</span> folder in our project directory.</p>
<p>The resulting <span class="pre">squared.h</span> file looks like:</p>
<pre class="brush: cpp; title: ; notranslate">
/* DO NOT EDIT THIS FILE - it is machine generated */
#include &amp;lt;jni.h&amp;gt;
/* Header for class org_edwards_research_demo_jni_SquaredWrapper */

#ifndef _Included_org_edwards_research_demo_jni_SquaredWrapper
#define _Included_org_edwards_research_demo_jni_SquaredWrapper
#ifdef __cplusplus
extern &amp;quot;C&amp;quot; {
#endif
/*
 * Class:     org_edwards_research_demo_jni_SquaredWrapper
 * Method:    squared
 * Signature: (I)I
 */
JNIEXPORT jint JNICALL Java_org_edwards_1research_demo_jni_SquaredWrapper_squared
  (JNIEnv *, jclass, jint);

#ifdef __cplusplus
}
#endif
#endif
</pre>
<p>The function name is annoying long, I agree.  We could eliminate a lot of that if we didn&#8217;t use a package in our java source, but I&#8217;m not really that concerned.</p>
<p>
<h2>Create C source</h2>
<p>Using the prototype generated by <span class="pre">javah</span>, we can implement our c source as follows:</p>
<pre class="brush: cpp; title: ; notranslate">
#include &amp;quot;squared.h&amp;quot;

JNIEXPORT jint JNICALL Java_org_edwards_1research_demo_jni_SquaredWrapper_squared
  (JNIEnv * je, jclass jc, jint base)
{
        return (base*base);
}
</pre>
<p>Note we have to give the parameters names and I arbitrarily chose <span class="pre">je</span> and<span class="pre">jc</span>, and chose <span class="pre">base</span> to replicate our java source parameter name.</p>
<p>In this case, the c source is very simple, but this tutorial is meant to illustrate how to include native code into your Android app and more complex c functions could be substituted with few modifications.</p>
<p>
<h2>Create <span class="pre">Android.mk</span></h2>
<p>After we create our c source file, we have to create our <span class="pre">Android.mk</span> file.  This file serves the as a sort of makefile for the Android build tools.  There are a number of sample <span class="pre">Android.mk</span> files in the <span class="pre">samples/</span> directory of the NDK and we&#8217;ll actually be using almost the exact lines from the <span class="pre">hello-jni</span> sample project.</p>
<p>Our <span class="pre">Android.mk</span> file looks like:</p>
<pre class="brush: plain; title: ; notranslate">
LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_MODULE    := squared
LOCAL_SRC_FILES := squared.c

include $(BUILD_SHARED_LIBRARY)
</pre>
<p>At this point, we have laid most of our groundwork for setting up and compiling the library. The next steps are actually creating the shared library, and implementing some simple UI code to show that our native function (<span class="pre">squared</span>) and derivative function (<span class="pre">to4</span>) work as expected.</p>
<p>This is continued in <a href="http://blog.edwards-research.com/2012/05/tutorial-android-jni-part-2/">Part 2</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2012/04/tutorial-android-jni/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Quick tip: &#8220;Commenting out&#8221; current command in&#160;terminal</title>
		<link>http://blog.edwards-research.com/2012/03/quick-tip-commenting-out-current-command-in-terminal/</link>
		<comments>http://blog.edwards-research.com/2012/03/quick-tip-commenting-out-current-command-in-terminal/#comments</comments>
		<pubDate>Sat, 24 Mar 2012 17:01:26 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[linux]]></category>
		<category><![CDATA[tips and tricks]]></category>
		<category><![CDATA[shortcuts]]></category>
		<category><![CDATA[terminal]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=632</guid>
		<description><![CDATA[So if you&#8217;re ever writing a command in a terminal, only to realize you forgot to do something first (e.g. switch to the right directory, change permissions etc.), you don&#8217;t have to delete the entire row, do what you forgot to do and retype. To some, this might be obvious, they might suggest holding down [...]]]></description>
			<content:encoded><![CDATA[<p>So if you&#8217;re ever writing a command in a terminal, only to realize you forgot to do something first (e.g. switch to the right directory, change permissions etc.), you don&#8217;t have to delete the entire row, do what you forgot to do and retype.</p>
<p>To some, this might be obvious, they might suggest holding down the left arrow until you reach the beginning of the line and &#8220;commenting it out&#8221; by inserting a # in front of the text.</p>
<p>But there are actually two quicker solutions, one somewhat obvious, and the other not so much.  The reason I&#8217;m writing this is just to point out the second one.</p>
<p>The first quick solution would be just to press the &#8220;Home&#8221; key and then insert the # symbol and press enter.  This is the pretty obvious method.  </p>
<p>The second method, which is actually a keystroke shorter, is to press Escape then the # symbol.  These two keys have the same result as the three keys in the first method.</p>
<p>Saving a single keystroke is really not the motivation for posting this tip, but rather the fact that some terminals, especially when first configuring your client / initialization scripts don&#8217;t accept the home key correctly (or quite often your client isn&#8217;t sending it correctly).</p>
<p>Anyway, in that situation, its helpful to have a backup option and the &#8220;Escape #&#8221; method comes in very handy.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2012/03/quick-tip-commenting-out-current-command-in-terminal/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Grabbing Flash files from&#160;cache</title>
		<link>http://blog.edwards-research.com/2012/03/grabbing-flash-files-from-cache/</link>
		<comments>http://blog.edwards-research.com/2012/03/grabbing-flash-files-from-cache/#comments</comments>
		<pubDate>Wed, 21 Mar 2012 19:17:31 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[python]]></category>
		<category><![CDATA[tips and tricks]]></category>
		<category><![CDATA[cache]]></category>
		<category><![CDATA[flash]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=624</guid>
		<description><![CDATA[Adobe has been making it increasingly difficult to grab flash files that are downloaded and cached, most likely for anti-piracy reasons. While I do not in any way support piracy, I have to say that my experience is that watching flash videos in something like VLC is such a better experience than watching it in [...]]]></description>
			<content:encoded><![CDATA[<p>Adobe has been making it increasingly difficult to grab flash files that are downloaded and cached, most likely for anti-piracy reasons.  While I do not in any way support piracy, I have to say that my experience is that watching flash videos in something like VLC is such a better experience than watching it in the browser plugin, especially in linux.</p>
<p>The Adobe plugin creates a secure temporary file &#8212; the typical way to do this is to (a) create a file, (b) open a file descriptor to it, (c) unlink (delete) the file.  As long as the file descriptor remains open, the file will be fine.  But once the file descriptor is closed, the bytes are free to be overwritten by the filesystem.    The last step of unlinking is in an attempt to limit other programs from accessing the file.</p>
<p>In our case, flash&#8217;s cache file is located in /tmp and named something like &#8220;FlashXXXXXXXXX&#8221;, for example: /tmp/FlashXX9Vj3jC</p>
<p>However, if you go into /tmp and run ls, it won&#8217;t be there &#8212; because it&#8217;s been deleted.</p>
<p>You can verify this by opening firefox, going to a site with a flash video, and running something like the following:</p>
<pre class="brush: bash; title: ; notranslate">
ls -l /proc/$(pidof plugin-container)/fd/ | grep Flash
</pre>
<p>For example, I did this and got:</p>
<pre>
l-wx------. 1 user user 64 Mar 20 22:41 17 -> /tmp/FlashXX9Vj3jC (deleted)
lrwx------. 1 user user 64 Mar 20 22:41 23 -> /tmp/FlashXXSUb8Wv (deleted)
</pre>
<p>Here we&#8217;re just looking at the plugin-container&#8217;s open file descriptors with &#8220;Flash&#8221; in them.</p>
<p>While you can&#8217;t access the cached files via /tmp/FlashXXXXXXXX, you <strong>can</strong> access them via the process file descriptor.  For example, in this case the file descriptors 17 and 23 correspond to the two cached files.</p>
<p>To copy the first one, you do something like:</p>
<pre class="brush: bash; title: ; notranslate">
cp /proc/$(pidof plugin-container)/fd/17 flashsave.flv
</pre>
<p>To make all of this a bit easier, I wrote the following python script:</p>
<pre class="brush: python; title: ; notranslate">
#!/bin/env python

import subprocess
import sys
import os
import shutil
from datetime import datetime

debug = False
outdir = '/tmp/flashsave'

# Great size_fmt function
# Source: http://stackoverflow.com/questions/1094841/reusable-library-to-get-human-readable-version-of-file-size
def sizeof_fmt(num):
    for x in ['bytes','KB','MB','GB']:
        if num &lt; 1024.0:
            return &quot;%3.1f%s&quot; % (num, x)
        num /= 1024.0
    return &quot;%3.1f%s&quot; % (num, 'TB')

# Find the pid of libflashplayer via plugin-container
ph = subprocess.Popen(['pidof', 'plugin-container'], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
[out,err] = ph.communicate()

# Ensure out is an int
if len(out) == 0:
    print('Process not found.')
    sys.exit(1)

pid = int(out)
print(&quot;Process found.  PID: %d&quot; % pid)

# Find open file descriptors
flash_fds = list()
filenames = os.listdir('/proc/%d/fd/' % (pid))
for f in filenames:
    fd = int(f)
    link_name = os.readlink('/proc/%d/fd/%d' % (pid, fd))

    if(debug): print(&quot;  %3d %-20s&quot; % (fd, link_name))

    if(link_name[0:10] == &quot;/tmp/Flash&quot;): flash_fds.append(fd)

# Display flash file descriptors
i = 0
for fd in flash_fds:
    path = '/proc/%d/fd/%d' % (pid, fd)
    size = os.stat(path).st_size

    print(&quot;Flash temp file found: %-20s [%s]&quot; % (path, sizeof_fmt(size)))

    dpath = &quot;%s/%s-%d.flv&quot; % (outdir, datetime.now().strftime(&quot;%Y-%m-%d-%H%I%S&quot;), i)
    shutil.copy(path, dpath)
    print(&quot;Copeid to: %s&quot; % (dpath))
    # Increment counter to try to keep filenames unique
    i = i+1
</pre>
<p>It&#8217;s really informal and could use some clean up, but it does the trick.  A few things to note: (1) you will want to wait until the video has finished loading before running this script.  You&#8217;ll only save what has been loaded &#8212; if you run it earlier, you&#8217;ll copy a half-complete file, and (2) you&#8217;ll need to either create the folder
<pre>/tmp/flashsave</pre>
<p> or update the <strong>outdir</strong> variable.  To run, simply save this as flash-save.py and type</p>
<pre class="brush: bash; title: ; notranslate">
./python flash-save.py
</pre>
<p>or make it executable with chmod and type</p>
<pre class="brush: bash; title: ; notranslate">
./flash-save.py
</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2012/03/grabbing-flash-files-from-cache/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Windows BSODs and the Driver&#160;Verifier</title>
		<link>http://blog.edwards-research.com/2012/03/windows-bsods-and-the-driver-verifier/</link>
		<comments>http://blog.edwards-research.com/2012/03/windows-bsods-and-the-driver-verifier/#comments</comments>
		<pubDate>Sun, 04 Mar 2012 20:48:23 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[windows]]></category>
		<category><![CDATA[BSOD]]></category>
		<category><![CDATA[driver verifier]]></category>
		<category><![CDATA[registry]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=613</guid>
		<description><![CDATA[For a while, I was getting random BSODs and some searching led me to decide to enable a feature called the driver verifier. [More info about Driver Verifier here] My understanding of the driver verifier is that, when a driver acts out of line, even a little bit, even if to an extent that otherwise [...]]]></description>
			<content:encoded><![CDATA[<div id="attachment_618" class="wp-caption aligncenter" style="width: 510px"><a href="http://blog.edwards-research.com/wp-content/uploads/2012/03/BSOD-Example.png" rel="lightbox[613]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/03/BSOD-Example.png" alt="" title="BSOD-Example" width="500" height="375" class="size-full wp-image-618" /></a><p class="wp-caption-text">The dreaded <em><strong>Blue Screen of Death</strong></em></p></div>
<p>For a while, I was getting random <a hreg="http://en.wikipedia.org/wiki/Blue_Screen_of_Death" target="_blank">BSODs</a> and some searching led me to decide to enable a feature called the driver verifier.  [<a href="http://support.microsoft.com/kb/244617" target="_blank">More info about Driver Verifier here</a>] My understanding of the driver verifier is that, when a driver acts out of line, even a little bit, even if to an extent that otherwise would be tolerated, Windows throws up a BSOD and lists the offending driver.</p>
<p>In my case, I was getting the <strong>Special Pool Detected Memory Corruption</strong> BSOD with no specific driver being listed.  The number of solutions I found online were almost unbelievable: everything from bad memory to corrupt MBR to corrupt CMOS settings.  In fact, none of these would have solved my issue.  But a few sites seemed to indicate that this meant that some driver was failing the verifier, but to determine which specific one, I had to examine the dump file that is generated once a BSOD is displayed.</p>
<p>So I loaded into a recovery session, and examined the dump file (C:\Windows\MEMORY.DMP &#8212; actually, it was D:\, but thats another story).  After analyzing it, <a href="http://msdn.microsoft.com/en-us/windows/hardware/gg463009" target="_blank">WinDbg</a> guessed that my mouse driver was causing the issue (RzSynapse.sys, presumably for the <a href="http://www.razerzone.com" target="_blank">Razer</a> mouse I had connected).</p>
<p>So I disconnect the mouse and restart hoping all would be well, but of course nothing is that easy and I immediately got another blue screen.  This time, however, it identified a driverm and a different one.  The problem here, however, is that the driver was for a remote management application I use, and not something I could easily disconnect to prevent it from being loaded.</p>
<p>So I know I need to update this driver, but I can&#8217;t do so easily because windows BSODs out before it even lets me log in.</p>
<p>So I decide to disable the verifier first, and then update the drivers.</p>
<p>In a command prompt in the recovery session I type
<pre>verifier /query</pre>
<p> but it says something to the effect of &#8220;no drivers are being verified&#8221;.  But that was simply not true, since the newest BSOD clearly says a driver failed verification.</p>
<p>I guess that the
<pre>verify</pre>
<p> command doesn&#8217;t work properly inside a recovery session, so I go to check the registry.  From pages <a href="http://www.carrona.org/verifier.html" target="_blank">like this</a> I find the registry path, so I fire up regedit, navigate to the where the keys should be and&#8230; they&#8217;re not there.</p>
<p>Well this complicates the matter.  On one hand, the BSOD indicates that driver verification is enabled, but neither the command line &#8220;verify&#8221; command nor the registry seems to think so.</p>
<p>After thinking about it for a few minutes, I recalled that <a href="http://support.microsoft.com/kb/927525" target="_blank">another page I had read previously</a> discussed loading a registry hive into regedit.  I didn&#8217;t think much of it at the time, but now it got me thinking that, maybe what regedit was displaying was a registry specific to the recovery session, and the registry that was used to boot windows was somewhere else.</p>
<p>I followed the steps outlined in this second article to load my system registry hive and voila, the driver verifier keys were, of course, present.  I promptly delete them, unload the registry hive, and restart the computer.  Hoping for the best, but fearing for the worst I walked out of the room to do some other things and when I came back, I was greeted by the glorious login screen &#8212; something a little bit earlier I hadn&#8217;t thought I&#8217;d see again without reformatting.</p>
<p>So, recap &#8212; lessons learned:</p>
<ul>
<li>In a recovery session, the registry regedit displays isn&#8217;t the registry you might expect.  You need to load external hives to edit them.  See the link above for how.</li>
<li>Driver Verifier is a decent trick to pin down random, unexplained BSODs, but the hassle it caused me makes me wish I simply made an effort to save more often and never even worried about curing them.  Simply throwing users to a BSOD seems harsh, especially when they may not cause BSODs had the verifier not been running.  I mean, it would be nice if I could &#8220;ignore&#8221; it, so I could then continue to boot windows and update the offending drivers.</li>
<li>There must be some recovery session information stored on non-primary disks, because when I disconnected my non-primary disks in an attempt to rule out hardware issues, the recovery session option was gone and in its place was a message asking me to boot from an install or recovery disk.  When I replaced the disk, the recovery session option returned.  Also interesting was the fact that, when I rearranged by drives in my BIOS correctly (primary on SATA order 1, secondary on SATA order 2) the recovery session again disappeared.  I&#8217;m sure this would be easy to look up and verify, but I&#8217;ve wasted enough time on this issue &#8212; maybe later.</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2012/03/windows-bsods-and-the-driver-verifier/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Script to Show All Font/Background Colors in&#160;Bash</title>
		<link>http://blog.edwards-research.com/2012/03/script-to-show-all-fontbackground-colors-in-bash/</link>
		<comments>http://blog.edwards-research.com/2012/03/script-to-show-all-fontbackground-colors-in-bash/#comments</comments>
		<pubDate>Thu, 01 Mar 2012 21:33:42 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[linux]]></category>
		<category><![CDATA[shell scripting]]></category>
		<category><![CDATA[tips and tricks]]></category>
		<category><![CDATA[bash]]></category>
		<category><![CDATA[colors]]></category>
		<category><![CDATA[gnome-terminal]]></category>
		<category><![CDATA[script]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=607</guid>
		<description><![CDATA[gnome-terminal makes up about 50% of my windows open on my linux boxes &#8212; but it defaults to a color scheme that is pretty dark if you choose to change the background to black (like I do). In order to adjust the color scheme, you can go into Edit -> Profile Preferences -> Colors Tab. [...]]]></description>
			<content:encoded><![CDATA[<p>gnome-terminal makes up about 50% of my windows open on my linux boxes &#8212; but it defaults to a color scheme that is pretty dark if you choose to change the background to black (like I do).  </p>
<p>In order to adjust the color scheme, you can go into Edit -> Profile Preferences -> Colors Tab.</p>
<p>However, its kind of hard to tell how the colors will look until they&#8217;re displayed on the screen with the black background.  The following simple script will generate a text in every font color, in every background color, and in all the styles:</p>
<pre class="brush: bash; title: ; notranslate">
#!/bin/bash

# The syntax for escaped color sequences looks like:
#
#    BLUE=&quot;\[&#92;&#48;33[0;34m\]&quot;
#
# Lets see what we can find...

NONE=&quot;&#92;&#48;33[0m&quot;

for COLOR in $(seq 30 40) ; do
    for STYLE in $(seq 0 1) 4 5 7; do
        TAG=&quot;&#92;&#48;33[${STYLE};${COLOR}m&quot;
        STR=&quot;Color:${COLOR}--Style:${STYLE}&quot;

        echo -ne &quot;${TAG}${STR}${NONE}  &quot;
    done
    echo
done
</pre>
<p>The output looks like:<br />
<div id="attachment_608" class="wp-caption alignnone" style="width: 665px"><a href="http://blog.edwards-research.com/wp-content/uploads/2012/03/bashcolors-tango.png" rel="lightbox[607]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/03/bashcolors-tango.png" alt="" title="bashcolors-tango" width="655" height="159" class="size-full wp-image-608" /></a><p class="wp-caption-text">Tango (default) theme</p></div></p>
<div id="attachment_609" class="wp-caption alignnone" style="width: 665px"><a href="http://blog.edwards-research.com/wp-content/uploads/2012/03/bashcolors-linuxconsole.png" rel="lightbox[607]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/03/bashcolors-linuxconsole.png" alt="" title="bashcolors-linuxconsole" width="655" height="157" class="size-full wp-image-609" /></a><p class="wp-caption-text">Linux Console theme</p></div>
<div id="attachment_610" class="wp-caption alignnone" style="width: 663px"><a href="http://blog.edwards-research.com/wp-content/uploads/2012/03/bashcolors-xterm.png" rel="lightbox[607]"><img src="http://blog.edwards-research.com/wp-content/uploads/2012/03/bashcolors-xterm.png" alt="" title="bashcolors-xterm" width="653" height="157" class="size-full wp-image-610" /></a><p class="wp-caption-text">Xterm theme</p></div>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2012/03/script-to-show-all-fontbackground-colors-in-bash/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Gnome 3 Delete Key &#8212; what&#160;happened!?</title>
		<link>http://blog.edwards-research.com/2012/02/gnome-3-delete-key-what-happened/</link>
		<comments>http://blog.edwards-research.com/2012/02/gnome-3-delete-key-what-happened/#comments</comments>
		<pubDate>Mon, 20 Feb 2012 23:46:40 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[linux]]></category>
		<category><![CDATA[tips and tricks]]></category>
		<category><![CDATA[bugs]]></category>
		<category><![CDATA[fail]]></category>
		<category><![CDATA[gnome]]></category>
		<category><![CDATA[gnome3]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=599</guid>
		<description><![CDATA[So I updated a few of my workstations to Fedora 16. I had been hesitating to upgrade from F14 because with F15 came Gnome 3, a pretty drastic departure from the traditional desktop environment we&#8217;re all used to. Some of the notable changes (and some of the first ones I found work arounds for) were: [...]]]></description>
			<content:encoded><![CDATA[<p>So I updated a few of my workstations to Fedora 16.  I had been hesitating to upgrade from F14 because with F15 came Gnome 3, a pretty drastic departure from the traditional desktop environment we&#8217;re all used to.  Some of the notable changes (and some of the first ones I found work arounds for) were:</p>
<ul>
<li>Removal of minimize and maximize button in title bar, leaving only the &#8220;x&#8221; close window button.</li>
<li>Removal of a task switching bottom panel</li>
<li>Removal of &#8220;Shutdown&#8221; / &#8220;Restart&#8221; from &#8230; Shutdown? menu &#8212; leaving only suspend</li>
<li>Forced grouping of windows by application when you&#8217;re alt tabbing.  Now 3 gnome-terminal sessions + firefox + gedit will show as 3 windows instead of 5 and require you to press down to descend into the individual windows of each group.</li>
<li>Remove the notification area available for applications and force all the applications that used it (sometimes, very cleverly) to rework their apps.  <a href="https://live.gnome.org/GnomeShell/Design/Guidelines/MessageTray/Compatibility">See this long list of &#8220;suggested changes&#8221; proposed by the Gnome devs.</a></li>
</ul>
<p></p>
<p>The list really goes on, but what really bothered me was that I found that the delete key in the file manager no longer worked.  To be clear, this isn&#8217;t exactly a <a href="http://www.gnome.org/" target="_blank">Gnome3 issue</a> but rather a <a href="http://live.gnome.org/Nautilus" target="_blank">Nautilus issue</a>, the filemanager for the gnome desktop.</p>
<p>At some point, the developers (at least those that accepted the patch) decided that they would diverge from decades of desktop environment tradition and change the shortcut from &#8220;Delete&#8221; to &#8220;Ctrl + Delete&#8221;.  The rationale being that &#8220;Delete&#8221; was too easy to press by accident, and since there was no notification that the files were moved to the trash, it would be transparent to the user that accidentally pressed delete.</p>
<p>The thing is, I think they correctly identified an issue: accidentally pressing delete could result in user confusion when they can&#8217;t find their files.  But what is amazing, is how they chose to address it &#8212; not by popping up a notification but by simply making it harder to accidentally (and intentionally) delete.</p>
<p>Its amazing because every OS I can think of already pops up a notification when you&#8217;re &#8220;soft-deleting&#8221; files.  By soft-deleting, I mean &#8220;moving to trash&#8221;, etc. &#8212; something that is completely reversible &#8212; and that&#8217;s the functionality we&#8217;re talking about with the (formerly) Del / (now) Ctrl+Del command.</p>
<p>But instead of popping up a simple notification, they chose the almost inexplicable route of confusing every desktop user who is even relatively comfortable with the limited subset of keyboard commands that &#8220;just work&#8221;.</p>
<p>Huge changes like this, I argue, require sufficient motivation.  In this case, the desire not to have a notification pop up is no where near sufficient.  It surprised me that this bug fell through the cracks, but it baffles me that its possible the Nautilus devs might think this is &#8220;working as intended&#8221; and not a bug.  This issue is not settled, <a href="https://bugzilla.gnome.org/show_bug.cgi?id=648658" target="_blank">as the bug is still technically open</a>, but the way the devs seem to be leaning is that this change is acceptable.</p>
<p>For example:</p>
<blockquote><p>Proposing WONTFIX. As written before this is not considered a bug but<br />
intentional behavior.</p>
<p>&#8211;André Klapper [developer] 2012-02-18 09:22:13 UTC </p></blockquote>
<p>But, to be honest, its not surprising.  The arrogant / selfish way that the gnome desktop has &#8220;evolved&#8221; in recent history should have prepared me for this.  From the outside looking in, it seems its just a bunch of people who think they know better about how the majority of the userbase <strong><em>should</em></strong> want to work &#8212; even despite an inordinate number of complaints and an immeasurable amount of time spent by third party developers in attempts to &#8220;bring back gnome2&#8243;.  More on that in the links below.</p>
<p>So in closing, I upgraded to Gnome3, but found myself unhappy as I expected would be the case.  In most of my workstations I&#8217;ve noticed a general decrease in performance clearly attributable to the gnome-shell.  I spent a considerable amount of time getting it to feel better, and it does, but I would really prefer my Gnome2 back.</p>
<p>That being said, there are two main options for Gnome3 users who hate the new UI.</p>
<p>The first is using &#8220;fallback mode&#8221;.  This gets the user extremely close to the Gnome2 look and feel.  Its not as polished as Gnome3 is, but it gets the job done.</p>
<p>The second is adding &#8220;shell extensions&#8221; to gnome to reproduce the functionality that Gnome longer ships with.  Specifically, this include a &#8220;Places&#8221; menu drop down, removing some of the annoying icons and menus that are there by default, restoring minimize and maximize buttons, restoring &#8220;shutdown&#8221; and &#8220;restart&#8221;, and (most importantly, imo) restoring the bottom panel task bar.</p>
<p>I&#8217;ve taken the latter approach and the best set of extensions I&#8217;ve found so far are the Mint Gnome Shell Extensions.  For a while, it seemed like Mint was going to back a Gnome2 fork (which was encouraging), but now it looks like they&#8217;ve decided to go with Gnome3, but reproduce the missing functionality through extensions.  These extensions are available on <a href="https://github.com/linuxmint/MGSE" target="_blank">their github site</a>, and can be easily installed on a fresh F16 install.</p>
<p>I only use a few of these, as well as a few from Gnome&#8217;s own <a href="https://extensions.gnome.org/" target="_blank">https://extensions.gnome.org/</a>.</p>
<p>While I have managed to get back 75-80% of the look and feel, the increased resource issue still a problem and I only expect it to get worse.  I use linux on my workstations so that I can get quck calculations at the expense of visual flair.  I&#8217;d be okay working (and do in fact often work) primarily from the command line.  These workstations had all of the visual flair disabled (Compiz, 3d rendering, transparency, etc) and ran like a charm.  Unfortunately, it looks as if this will not be the case with Gnome3.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2012/02/gnome-3-delete-key-what-happened/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Preventing Wildcard Expansion / Globbing in Shell&#160;Scripts</title>
		<link>http://blog.edwards-research.com/2011/05/preventing-globbing/</link>
		<comments>http://blog.edwards-research.com/2011/05/preventing-globbing/#comments</comments>
		<pubDate>Wed, 04 May 2011 01:50:26 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[linux]]></category>
		<category><![CDATA[shell scripting]]></category>
		<category><![CDATA[tips and tricks]]></category>
		<category><![CDATA[expanding]]></category>
		<category><![CDATA[globbing]]></category>
		<category><![CDATA[shell script]]></category>
		<category><![CDATA[wildcard]]></category>
		<category><![CDATA[wildcard expansion]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=581</guid>
		<description><![CDATA[I wanted to pass a string containing a wildcard to a shell script and not worry about the shell automatically globbing it for me. For example, lets consider a simple script, globme.sh which is in a directory containing: globme.sh notes.txt phonebook.csv todo.txt Let&#8217;s see how the script reacts to different inputs. First, lets look at [...]]]></description>
			<content:encoded><![CDATA[<p>I wanted to pass a string containing a wildcard to a shell script and not worry about the shell automatically <a href="http://en.wikipedia.org/wiki/Glob_%28programming%29">globbing</a> it for me.</p>
<p>For example, lets consider a simple script, <strong>globme.sh</strong></p>
<pre class="brush: bash; title: ; notranslate">
#!/bin/bash

echo &quot;1[${1}]&quot;
echo &quot;@[${@}]&quot;
echo
</pre>
<p>which is in a directory containing:</p>
<pre>
globme.sh
notes.txt
phonebook.csv
todo.txt
</pre>
<p>Let&#8217;s see how the script reacts to different inputs.  First, lets look at what it does without any wildcards:</p>
<pre>
$ ./globme.sh Not Wildcards
1[Not]
2[Wildcards]
@[Not Wildcards]
</pre>
<p>It works as one might expect, the 2nd space-separated argument passed to the script is placed into $2.  If you expect a certain value to always be at $2, no matter what, you might be surprised when you call the script with something like:</p>
<pre>
$ ./globme.sh *.txt red
</pre>
<p>and find out that $2 is not &#8220;red&#8221;, but in fact the name of a file in your current directory:</p>
<pre>
$ ./globme.sh *.txt socket
1[notes.txt]
2[todo.txt]
@[notes.txt todo.txt socket]
</pre>
<p>But note the fact that, if your wildcard <strong>does not</strong> match set of files in your current directory, it will be passed to the script as-is:</p>
<pre>
$ ./globme.sh *.py socket
1[*.py]
2[socket]
@[*.py socket]
</pre>
<p>Well this is not good.  The same file and same input acts two different ways based what directory you&#8217;re in.  Of course, one solution would be to always remember to enclose your arguments in quotes (single or double):</p>
<pre>
$ ./globme.sh '*.txt' socket
1[*.txt]
2[socket]
@[*.txt socket]

$ ./globme.sh "*.txt" socket
1[*.txt]
2[socket]
@[*.txt socket]
</pre>
<p>But what if you didn&#8217;t want to require this?  What if there were no circumstances under which you wanted the shell to expand wildcards for you?  I&#8217;ll bring you slowly through the steps you might have taken had you not found this tutorial, but if you&#8217;re in a rush, you can skip to the end to my favorite solution.</p>
<p>After some searching, you may have found out that there is a shell option (f) that you can set that will disable this behavior.  To do this, simply call <strong>set -f</strong>, as in:</p>
<pre>
$ ./globme.sh * *
1[globme.sh]
2[notes.txt]
@[globme.sh notes.txt phonebook.csv todo.txt globme.sh notes.txt phonebook.csv todo.txt]

$ set -f

$ ./globme.sh * *
1[*]
2[*]
@[* *]
</pre>
<p>So you could always call <strong>set -f</strong> before every <strong>globme.sh</strong>, but that gets tedious.</p>
<p>Okay, so then you could <a href="http://tldp.org/LDP/abs/html/aliases.html" target="_blank">alias it</a> by adding the following to your .bashrc / .bash_profile file:</p>
<pre class="brush: bash; title: ; notranslate">
alias globme='set -f; /path/to/globme.sh'
</pre>
<p>Which is better, since you don&#8217;t have to remember to call another program before globme, and even if you remember to call another program, you don&#8217;t have to remember the program or syntax.</p>
<p>But now you run into the problem where your shell option persists after your command.  So while you might expect that <strong>cat *</strong> prints the contents of each file in your current directory, you&#8217;ll get an error:</p>
<pre>
$ cat *
cat: *: No such file or directory
</pre>
<p>This problem is exacerbated by the fact that subshells that spawn from your current shell inherit those options.  So shell scripts, etc. that expect and rely a certain behavior will not function correctly.</p>
<p>Okay, so one solution would be to remember to clear the shell option after each time using <strong>set +f</strong>.  This would work, but it&#8217;s terribly annoying to have to remember.</p>
<p>If you&#8217;re wondering whether you can modify your alias to also clear the option, perhaps like:</p>
<pre class="brush: bash; title: ; notranslate">
alias globme='set -f; /path/to/globme.sh; set+f;'
</pre>
<p>You&#8217;ll be disappointed to learn that you cannot.  Your arguments are added after the alias, so you&#8217;d get something like</p>
<pre>
$ set -f
$ /path/to/globme.sh
$ set+f
$ YourFirstArgument YourSecondArgument ...
</pre>
<p>So maybe you&#8217;ll drop the alias and define <a href="http://tldp.org/LDP/abs/html/functions.html" target="_blank">a function</a> in your .bashrc / .bash_profile to handle this for you.  Maybe something like</p>
<pre class="brush: bash; title: ; notranslate">
globme()
{
    set -f
    /path/to/globme.sh
    set+f
}
</pre>
<p>You&#8217;d be further disappointed when you found out that the shell expanded your wildcards before they were passed to the function, so you&#8217;d be setting the -f option too late!</p>
<h2>Working (but not optimal solutions)</h2>
<p>My first solution was to edit my script to respawn the shell upon exiting.  Simply put, I would use the shell&#8217;s <a href="http://ss64.com/bash/exec.html" target="_blank"><strong>exec</strong> command</a> to exit into a new instance of the shell.  Specifically, I would add</p>
<pre class="brush: bash; title: ; notranslate">
exec /bin/bash
</pre>
<p>or to generalize it (perhaps unnecessarily),</p>
<pre class="brush: bash; title: ; notranslate">
exec ${SHELL}
</pre>
<p>at the end of the program.</p>
<p>The problem with this solution is that you would lose any environment variables you had set.  For example:</p>
<pre class="brush: bash; title: ; notranslate">
$ TEST=&quot;Testing&quot;
$ echo $TEST
Testing
$ exec ${SHELL}
$ echo $TEST
(blank line)
</pre>
<p>This is not expected behavior unless you explicitly respawn your shell instance.  Also, consider that your script may have multiple exit points (perhaps erroring out at various points, etc) &#8212; in that case you&#8217;d need to add the line at every exit point.  Further complicating the problem is that by doing this, you&#8217;re losing the exit-code of your program.  Whereas before you could have used <strong>return 1</strong> to indicate an error (which can be viewed by <strong>echo $?</strong> as the next command after your program), now your exec will have to be in it&#8217;s place.</p>
<p>So next, my almost-done solution integrated both aliases and functions:</p>
<pre class="brush: bash; title: ; notranslate">
alias globme='set -f; g'
g(){ /path/to/globme.sh &quot;$@&quot;; set +f; }
</pre>
<p>Here, the alias allows us to set the shell option first, so the wildcards are not expanded.  Then, the function g() is called, which is simply globme, with &#8220;$@&#8221; as the argument (will get to that in a second), followed by the command to clear the shell option.</p>
<p>This works.  Perfectly.  To check, you could type</p>
<pre>
echo $-
</pre>
<p>and if you see an &#8216;f&#8217;, the option is set (remember, it&#8217;s set with -f and cleared with +f) &#8212; if you don&#8217;t, it&#8217;s cleared.</p>
<p>The &#8220;$@&#8221; expands to the arguments that were passed to the function g &#8212; which in this case, are the arguments you passed at the prompt!</p>
<h2>Cut to the chase!</h2>
<p>Lastly, I realized that it might be a little annoying to have a function and an alias for each script that you wished behave like this.  To generalize our lines, I changed them to the following:</p>
<pre class="brush: bash; title: ; notranslate">
reset_expansion(){ CMD=&quot;$1&quot;; shift; $CMD &quot;$@&quot;; set +f; }
alias globme='set -f; reset_expansion /path/to/globme.sh'
</pre>
<p>which basically does the same thing, but it allows you to reuse the reset_expansion() function.  For example if you had a second script that you wanted to behave the same way named <strong>newscript</strong>, you would only need to add the following to your .bashrc / .bash_profile:</p>
<pre class="brush: bash; title: ; notranslate">
alias newscript='set -f; reset_expansion /path/to/newscript'
</pre>
<p>And that&#8217;s all she wrote.  Now, the bash philosophers out there will will say something along the lines of &#8220;Just enclose wildcard arguments in quotes&#8221;, which has a lot of merit, but I&#8217;d rather add these lines and not worry about it.  Enjoy!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2011/05/preventing-globbing/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Colored Output in C/C++ (Part&#160;3)</title>
		<link>http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-3/</link>
		<comments>http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-3/#comments</comments>
		<pubDate>Sun, 24 Apr 2011 08:44:37 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[c++]]></category>
		<category><![CDATA[programming]]></category>
		<category><![CDATA[tips and tricks]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=569</guid>
		<description><![CDATA[This is part 3 of a 3 part series in printing in color in C/C++ (Continued from Part 2) cprintf.h cprintf_test.cpp Which looks like this in gnome-terminal: Leveraging some of the benefits of c++, I was able to streamline some of the ColorSet construction that took up an annoying amount of lines with the struct [...]]]></description>
			<content:encoded><![CDATA[<p><em>This is part 3 of a 3 part series in printing in color in C/C++</em></p>
<p>(Continued from <a href="http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-2/">Part 2</a>)</p>
<p><strong>cprintf.h</strong></p>
<pre class="brush: cpp; title: ; notranslate">
////////////////////////////////////////////////////////////////////////////////////////////////////
//
// (C)2011 Edwards Research Group
// You are licensed to use this work under a CC-BY-SA License.
// See: http://blog.edwards-research.com/about/
//      http://creativecommons.org/licenses/by-sa/3.0/us/
//
////////////////////////////////////////////////////////////////////////////////////////////////////

#include &lt;stdio.h&gt;
#include &lt;stdarg.h&gt;

enum CP_ColorType {BLACK   = 0,
                   RED     = 1,
                   GREEN   = 2,
                   YELLOW  = 3,
                   BLUE    = 4,
                   MAGENTA = 5,
                   CYAN    = 6,
                   WHITE   = 7,
                   UNDEF   = -1};

enum CP_AttrType  {NONE    = 0,
                   BOLD    = 1,
                   DIM     = 2,
                   UNDERLINE = 4,
                   BLINK   = 5,
                   REVERSE = 7};

class ColorSet
{
public:
    CP_ColorType _fg;
    CP_ColorType _bg;
    CP_AttrType  _attr;

    // Default Constructor
    ColorSet(){ set(UNDEF,UNDEF,NONE); }

    // 1 param constructor
    ColorSet(CP_ColorType fg){ set(fg,UNDEF,NONE); }

    // 2 param constructors
    ColorSet(CP_ColorType fg, CP_AttrType attr){ set(fg,UNDEF,attr); }
    ColorSet(CP_ColorType fg, CP_ColorType bg) { set(fg,bg,NONE); }

    // 3 param constructor
    ColorSet(CP_ColorType fg, CP_ColorType bg, CP_AttrType attr){ set(fg,bg,attr); }

    void set(CP_ColorType fg, CP_ColorType bg, CP_AttrType attr)
    {
        _fg   = fg;
        _bg   = bg;
        _attr = attr;
    }

    // Cool Wrapper
    void cprintf(const char * fmt, ...)
    {
        va_list args;
        va_start(args, fmt);

        cp_init();
        vprintf(fmt, args);
        cp_rst();

        va_end(args);
    }

private:
    void cp_init(void)
    {
        if(_bg != -1){
            printf(&quot;%c[%d;%d;%dm&quot;,27,_attr,(30+_fg),(40+_bg));
        }
        else{
            printf(&quot;%c[%d;%dm&quot;,27,_attr,(30+_fg));
        }
    }

    void cp_rst(void)
    {
        printf(&quot;%c[%dm&quot;, 27, 0);
    }
};
</pre>
<p><strong>cprintf_test.cpp</strong></p>
<pre class="brush: cpp; title: ; notranslate">
////////////////////////////////////////////////////////////////////////////////////////////////////
//
// (C)2011 Edwards Research Group
// You are licensed to use this work under a CC-BY-SA License.
// See: http://blog.edwards-research.com/about/
//      http://creativecommons.org/licenses/by-sa/3.0/us/
//
////////////////////////////////////////////////////////////////////////////////////////////////////

#include &lt;stdio.h&gt;

#include &quot;cprintf.h&quot;

int main(void)
{
    ColorSet alert(RED, BOLD);
    ColorSet warn(YELLOW, UNDERLINE);

    printf(&quot;\n&quot;);
    printf(&quot;Unformatted...\n&quot;);
    alert.cprintf(&quot;THIS IS AN ALERT!\n&quot;);
    warn.cprintf(&quot;THIS IS A WARNING.\n&quot;);
    printf(&quot;\n&quot;);

    int i,j;
    for(i=0; i&lt;8; i++)
    {
        for(j=0; j&lt;8; j++)
        {
            if(j == 3 | j == 6){ continue; }
            ColorSet((CP_ColorType)i, (CP_AttrType)j).cprintf(&quot;FG=%d,A=%d&quot;, i, j);
            printf(&quot;    &quot;);
        }
        printf(&quot;\n&quot;);
    }
    printf(&quot;\n&quot;);

    warn.cprintf(&quot;Much later, I can simply use warn without having to lookup the style I last used.\n&quot;);

    // Example Showing real-time definition and overloaded constructors
    ColorSet(YELLOW, RED).cprintf(&quot;Yellow on Red...&quot;);
    printf(&quot;\n&quot;);
    ColorSet(BLUE, REVERSE).cprintf(&quot;Reversed Blue...&quot;);
    printf(&quot;\n&quot;);

    return 0;
}
</pre>
<p>Which looks like this in gnome-terminal:<br />
<a href="http://blog.edwards-research.com/wp-content/uploads/2011/04/2011-04-24-ER-cprintf-cpp-gterm.png" rel="lightbox[569]"><img src="http://blog.edwards-research.com/wp-content/uploads/2011/04/2011-04-24-ER-cprintf-cpp-gterm.png" alt="" title="2011-04-24-ER-cprintf-cpp-gterm" width="594" height="244" class="alignnone size-full wp-image-579" /></a></p>
<p>Leveraging some of the benefits of c++, I was able to streamline some of the ColorSet construction that took up an annoying amount of lines with the struct style.  </p>
<p>I also changed the #defines to an enum to make the compile-time checking more intelligent. </p>
<p>Lastly, the overloaded constructors allow me to use a 2-parameter constructor for both (FOREGROUND, BACKGROUND) and (FOREGROUND, ATTRIBUTE) style.</p>
<p>Now, if I were to make this production code, I&#8217;d hide my member variables, expose getter and setter interfaces (if necessary), re-prefix the enum&#8217;s to avoid conflicts, and separate out the implementation into a .cpp file &#8212; but this was really just a proof-of-concept thing.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-3/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Colored Output in C/C++ (Part&#160;2)</title>
		<link>http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-2/</link>
		<comments>http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-2/#comments</comments>
		<pubDate>Sun, 24 Apr 2011 07:58:57 +0000</pubDate>
		<dc:creator>Jim</dc:creator>
				<category><![CDATA[c]]></category>
		<category><![CDATA[programming]]></category>
		<category><![CDATA[tips and tricks]]></category>

		<guid isPermaLink="false">http://blog.edwards-research.com/?p=562</guid>
		<description><![CDATA[This is part 2 of a 3 part series in printing in color in C/C++ (Continued from Part 1) In order to be able to specify a &#8220;color set&#8221;, and avoid having to define parameters I didn&#8217;t want, my next iteration was to move to a structure-based approach: cprintf.h cprintf_test.c Which turned out like this [...]]]></description>
			<content:encoded><![CDATA[<p><em>This is part 2 of a 3 part series in printing in color in C/C++</em></p>
<p>(Continued from <a href="http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-1/">Part 1</a>)</p>
<p>In order to be able to specify a &#8220;color set&#8221;, and avoid having to define parameters I didn&#8217;t want, my next iteration was to move to a structure-based approach:</p>
<p><strong>cprintf.h</strong></p>
<pre class="brush: cpp; title: ; notranslate">
////////////////////////////////////////////////////////////////////////////////////////////////////
//
// (C)2011 Edwards Research Group
// You are licensed to use this work under a CC-BY-SA License.
// See: http://blog.edwards-research.com/about/
//      http://creativecommons.org/licenses/by-sa/3.0/us/
//
////////////////////////////////////////////////////////////////////////////////////////////////////

#include &lt;stdio.h&gt;
#include &lt;stdarg.h&gt;

#define CLR_BLACK   0
#define CLR_RED     1
#define CLR_GREEN   2
#define CLR_YELLOW  3
#define CLR_BLUE    4
#define CLR_MAGENTA 5
#define CLR_CYAN    6
#define CLR_WHITE   7

#define ATTR_NONE       0
#define ATTR_BOLD       1
#define ATTR_DIM        2
#define ATTR_UNDERLINE  4
#define ATTR_BLINK      5
#define ATTR_REVERSE    7

typedef struct{
    int fg;
    int bg;
    int attr;
} cset_t;

cset_t * cset_init(cset_t * cs)
{
    cs-&gt;fg = -1;
    cs-&gt;bg = -1;
    cs-&gt;attr = -1;
    return cs;
}

cset_t * cset_setfg(cset_t * cs, int fg)
{
    cs-&gt;fg = fg;
    return cs;
}

cset_t * cset_setbg(cset_t * cs, int bg)
{
    cs-&gt;bg = bg;
    return cs;
}

cset_t * cset_setattr(cset_t * cs, int attr){
    cs-&gt;attr = attr;
    return cs;
}

void cprint_init(cset_t * cs)
{
    if(cs-&gt;bg != -1){
        printf(&quot;%c[%d;%d;%dm&quot;,27,cs-&gt;attr,(30+cs-&gt;fg),(40+cs-&gt;bg));
    }
    else{
        printf(&quot;%c[%d;%dm&quot;,27,cs-&gt;attr,(30+cs-&gt;fg));
    }
}

void cprint_rst(void)
{
    printf(&quot;%c[%dm&quot;, 27, 0);
}

int cprintf(cset_t * cs, char * fmt, ...)
{
    va_list args;
    va_start(args, fmt);

    cprint_init(cs);
    vprintf(fmt, args);
    cprint_rst();

    va_end(args);
}
</pre>
<p><strong>cprintf_test.c</strong></p>
<pre class="brush: cpp; title: ; notranslate">
////////////////////////////////////////////////////////////////////////////////////////////////////
//
// (C)2011 Edwards Research Group
// You are licensed to use this work under a CC-BY-SA License.
// See: http://blog.edwards-research.com/about/
//      http://creativecommons.org/licenses/by-sa/3.0/us/
//
////////////////////////////////////////////////////////////////////////////////////////////////////

#include &lt;stdio.h&gt;

#include &quot;cprintf.h&quot;

void main(void)
{
    // Example Showing Individual Configuration
    cset_t alert;
    cset_init(&amp;alert);
    cset_setfg(&amp;alert, CLR_RED);
    cset_setattr(&amp;alert, ATTR_BOLD);

    // Example Showing Cascaded Configuration
    cset_t warn;
    cset_setattr(cset_setfg(cset_init(&amp;warn), CLR_YELLOW), ATTR_UNDERLINE);

    printf(&quot;Unformatted...\n&quot;);
    cprintf(&amp;alert, &quot;THIS IS AN ALERT!\n&quot;);
    cprintf(&amp;warn,  &quot;THIS IS A WARNING.\n&quot;);
    printf(&quot;\n&quot;);

    cset_t loop;
    cset_init(&amp;loop);
    int i,j;
    for(i=0; i&lt;8; i++)
    {
        for(j=0; j&lt;8; j++)
        {
            if(j == 3 | j == 6){ continue; }
            cset_setfg(&amp;loop, i);
            cset_setattr(&amp;loop, j);
            cprintf(&amp;loop, &quot;FG=%d,A=%d&quot;, i, j);
            printf(&quot;    &quot;);
        }
        printf(&quot;\n&quot;);
    }
    printf(&quot;\n&quot;);

    cprintf(&amp;warn, &quot;Much later, I can simply use &amp;warn without having to lookup the style I last used.\n&quot;);

    return;
}
</pre>
<p>Which turned out like this (in PuTTY):<br />
<a href="http://blog.edwards-research.com/wp-content/uploads/2011/04/2011-04-24-ER-cprintf-c2.png" rel="lightbox[562]"><img src="http://blog.edwards-research.com/wp-content/uploads/2011/04/2011-04-24-ER-cprintf-c2.png" alt="" title="2011-04-24-ER-cprintf-c2" width="581" height="217" class="alignnone size-full wp-image-564" /></a></p>
<p>I liked this solution better than my first.  Here I was able to define program-wide color schemes (e.g. alert, warn) and simply reference them on future calls to cprintf().  I could have also added a one-time-use &#8220;constructor&#8221; that would return a static pointer to a structure of type cset_t based off 3 integers for inline coding.</p>
<p>Something like:</p>
<pre class="brush: cpp; title: ; notranslate">
cset_t onu;

cset_t * cset(int fg, int bg, int attr)
{
    onu.fg = fg;
    onu.bg = bg;
    onu.attr = attr;
    return &amp;onu;
}
</pre>
<p>So that I could also do something like the following in my main program:</p>
<pre class="brush: cpp; title: ; notranslate">
cprintf(cset(CLR_YELLOW, CLR_RED, ATTR_NONE), &quot;Yellow on Red...&quot;);
</pre>
<p>As for my C version, this is where I left it &#8212; my next iteration was in C++.</p>
<p>Continue to <a href="http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-3/">Part 3</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.edwards-research.com/2011/04/colored-output-in-cc-part-2/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

