Two quotes and the cognitive dissonance between them

I came across two quotations. Here they are:

Nothing is particularly hard if you divide it into small jobs.
- Henry Ford

If the brain were so simple we could understand it, we would be so simple we couldn’t.
- Lyall Watson

I noticed I had written both of these on the same sheet of paper. Individually I agree with each of them. In particular, I like the Lyall Watson quote, which is both amusing and well thought out. In a few words it dismisses the hopes and dreams of psychologists, neuroscientists, artificial intelligence researchers, and projects that strive toward true self-replicating machines. At least, it does all that if you choose to take it that far. But it also preserves the magic and complexity of the human mind. To my ear, it both resonates with and contradicts Henry Ford’s quote.

I admit I’m taking two things completely out of context. Ford was talking about manufacturing, and Watson was talking about the brain. But let’s give ourselves license here. We’ll take these quotes out of the rich contexts from which they were generated, and set them together in an empty room.

Which, if either, is true? Or can they agree on some level?

Complex decisions have at their root a mass of very simple ones. I’ll hold that hypothesis out for criticism, but as far as I understand the mind it must be true. We don’t have the capacity to hold all of world politics in out minds at once, for example. It’s just too big a subject. Perhaps that’s why we get annoyed when people spout sweeping generalities rather than using detailed arguments. “How did you come to that conclusion,” we ask, or “what makes you say that?” These are the questions we ask in response to a general statement, particularly one we disagree with, and they imply that whole world-views hinge on the smaller details. We question unpopular decisions in the same way.

We act based on our understanding of how the action will affect a series of surrounding events and circumstances. Sometimes we vacillate in the decision-making process because it is difficult to find an ideal solution. “If I tell Jenny about Bob and Jean, I’ll be betraying Bob; but if Jenny finds out later that I know, she’ll never speak to me again.” We are alternately pulled toward two different solutions, based on which consequence we are evaluating in a given moment. In these situations, we often rely on tie-breakers from the realm of morality or experience. “Honesty is always the best policy; I’ll just be honest and Bob will have to understand.” Or: “Putting my nose in other people’s business has only ever caused trouble. I can’t be involved in their problems; I won’t say anything.” One simple factor added into the equation gives us the ability to break the decision loop and return to action.

Maybe we can’t fully understand something as complex as the human brain. I’m not positive we can understand something as complex as a modern automobile or a computer chip, at least not all at once. We can understand their parts. We can even understand fairly intricate parts at one time, but to visualize the whole we are forced to let the parts fade into the background, become blurred, and at best to remember some detail about how they can interact with the parts around them. Often, we switch to a serial mode of thinking. We see the things as a series of events because we can not focus our attention on the entire thing without losing something. We come up with something like: Combustion drives the piston, which turns a shaft, where the force is converted via belts and gears to an axle, which rotates a tire, which translates torque to linear motion along the road. Such an understanding is a simplified construct. The elements of time and synchronicity are lost in the translation, so we have a simple series rather than an orchestra of simultaneous events.

None of that means we can’t make a car, however. I question whether anyone can fully comprehend a car in a single thought, because of the nature of comprehension and of thoughts. But we can still understand a car in the way that we’re good at understanding things, in parts. Computers are similarly gifted, perhaps as a reflection of their makers. So can we make a computer that thinks, and that passes the Turing test, and that passes whatever tests we come up with after that when our pride is injured by the idea that machines could some day rival us as thinkers? Well, nothing is particularly difficult if you divide it into small jobs.

Posted in Uncategorized | Leave a comment

Flash and Flash server security

Here are 5 keys that I think are the crux of non-annoying flash security (annoying security would be the kind that never works because of DRM, pops up password dialogs in your face, causes users to suffer or jump through hoops, etc). They basically fit together to form a whole, but if you implemented one or more you would be at least slightly better off (the estimated age of a capable attacker might rise from 6 to 12 years old).

1. Serve your flash files to otherwise authenticated users through Apache, Tomcat, a CMS or LMS, or your blog’s security plugin. Preferably to a “trusted” (synonym for non-technical? j/k) user base.
2. Use SWF verification if your server supports it (Adobe’s does, Red5 doesn’t as of this writing). You’ll only serve SWF documents that you’ve whitelisted, and others will not be able to get content directly from the rtmp/flash server. This will be even more useful if combined with #3.
3. Domain lock your flash files so that they can only run when served from your domain. People can get around this, but if you use SWF verification with it, then getting around the domain lock invalidates the SWF to the server. That means an attacker would still have to find a way around the verification to use a counterfeit SWF, which raises the bar a bit. While you’re at it, it won’t hurt to use an obfuscation/encryption tool to prevent casual decompiling and reading publish() string names, server addresses, etc. I wouldn’t count on it deterring a real attacker though.
4. Put restraints on anything else that’s practical for your use – stream names, virtual hosts, etc.
5. Consider using SSL, RTMPE. I admit I’m not at the moment, but I’m not holding business meetings over the connection either.

It seems like there are 1,000 pages written about configuring a crossdomains.xml… don’t believe that will actually slow anyone down. But the things I list above are worth looking in to.

Posted in Uncategorized | Leave a comment

Laggy file navigation at startup with xfce Thunar: fix

This applies to the last two or three distributions of Linux that use Thunar as file manager, notably Xubuntu or others using Xfce for the desktop. The problem is that the first time you open the file manager, you have to wait a very long time to see anything. This can persist for several minutes after booting, even with multicore systems with lots of RAM. Some people also get error messages.

The reason seems to be that Thunar is waiting for gvfs-xxx to return with network devices. Rather than allowing the user to breathe by showing them the interface, it does nothing until this process returns (30 seconds to several minutes). Reportedly there is a bug with one of the gvfs modules that I won’t pretend to have analyzed in detail. The Thunar behavior is known to the developers, and I believe they are working on it… but what to do for now?

Well here’s a fix that works for me on Xubuntu 11.10. Do this:

sudo nano /usr/share/gvfs/mounts/network.mount

(with editor of your choice if nano doesn’t do it for you)… This file is only a few lines long. Change this:

Exec=/some/exec
AutoMount=true

to this:

#Exec=/some/exec
Exec=''
AutoMount=false

The next time you reboot, you’ll start off with a usable and responsive GUI. Yay.

One or the other change to network.mount might even be enough. Note that this will disable Thunar’s (ill-fated) search for remote drives — not much of a fix if you need that functionality, I admit. But if you need your file manager to mount remote drives, you can always try another manager.

Posted in Uncategorized | Leave a comment

VirtualBox 4.1.8

VirtualBox is my new best friend. Soooo many 64-bittish problems, not to mention OS X problems (if developing anything other than Cocoa) can be solved simply by installing 32-bit linux in VirtualBox. Now to see if my Py2App distributions actually run on the mac :)

Posted in Uncategorized | Leave a comment

Forcing 32 bit Python in OS X 10.6 +

Lots of python libraries fail to install or fail to work under 64 bit python. Here’s a cheesy non-programmatic hack to make 32-bit python the default.

1. Find the path to the python installation you want to default to 32-bit mode in your .bash_profile

nano .bash_profile

Mine is at /Library/Frameworks/Python.framework/Versions/2.7/bin

2. Go to the python installation in Finder. Observe the aliases (shortcuts / symlinks) to various python configurations. If you’re not sure what you’re looking for, stop and go find out about aliases and symlinks, what they are, and what they look like in OS X (obligatory “don’t proceed if you don’t know what you’re doing”).

3. Rename the alias called “python” to “python-64″. There is no existing alias with that name because “python” defaults to the 64-bit configuration whenever possible.

4. Right click “python-32″ or, if you prefer, “python2.7-32″ (which is not an alias, but is what the alias points to). Select “Make Alias”. Rename the new alias “python”.

5. Now any time you type “python” in the Terminal, 32-bit python will start. Even better, when other programs start python in various ways, or the python launcher starts, they will default to 32-bit python.

6. If you ever want to go back and default to 64-bit again, just delete your python alias and remove “-64″ from “python-64″.

By the way, don’t believe what you read in the man pages about this stuff:

# this doesn't work!
defaults write com.apple.versioner.python Prefer-32-Bit -bool yes
# neither does this!
export VERSIONER_PYTHON_PREFER_32_BIT=yes

The Mac versioner stuff only applies to the Mac pre-installed python. It will not have any effect on your python 2.7 installation!

And one final caveat. If you’ve installed libraries under 64-bit python, you might get a “wrong architecture” error running in 32-bit mode. You can either run those programs under 64-bit, or assuming you can install 32-bit configurations of your libraries, do that.

Posted in Uncategorized | Leave a comment

ndexr – index a directory and output a json file of its contents

New python project at https://sourceforge.net/projects/ndexr/

Currently it indexes a directory specified in interactive mode or by a config file, and writes a json file cataloging the directory’s contents. You can also specify the output file and the files types to index.

It is made to be easy to extend with your own scripts… ie: if you want to recursively index a directory tree you can. If you want to index files on a server and send them once a week to some other server you can. If you want to use it to let clients search a directory without actually having access to it, you certainly can (you’ll have to supply apache or some other web server obviously).

I’ll probably extend it to automatically handle recursive indexing, and optional indexing of directories (as of right now it indexes files only, because that’s what I needed it to do today :)

It’s simple, not much code, and its only job will stay in the domain of indexing files and spitting out json. Check it out if you think it’s useful to you.

Posted in Uncategorized | Leave a comment

Stretching a 1-pixel image to make a resizeable border or shadow

This comes up a lot, so I’m positing an image to illustrate the idea.

Here’s my related stack overflow answer, which uses the technique to make a shadow around a UITableView section of arbitrary size and shape.

Posted in Uncategorized | 2 Comments

Batch plist to JSON conversion

Posted this to sourceforge last night:

plist2json: Batch convert plist files to JSON

Feature list:

  • Convert any number of plist’s to json
  • Command line – type a directory to convert or drag and drop folder to Terminal
  • Works with OS X, should work fine in most Linux distros
  • Compact, easy to modify for your own needs

It’s easier to use than the rough one-at-a-time version I posted before. Enjoy.

Posted in Uncategorized | 1 Comment

Convert plist to JSON

EDIT: see my plist2json post for a better version

Here’s a python program to convert a plist to JSON. You’ll need to type in the input and output filenames in the GUI (ie: /Users/bob/myDirectory/file.plist). It will overwrite the output file if it already exists. If anyone wants a version for batch processing, feel free to modify it or send me a request. Tested in Python 2.7.2.

# By Rab Beverly: http://www.robertbeverly.com
# Author assumes no responsibility for damages.
# Use this code however you wish.
# Attribution is not required.

import json
from plistlib import readPlist
import StringIO
import Tkinter

class Converter:

    def __init__(self):
        """ ... """
        self.root = root = Tkinter.Tk()
        root.title('Converter')
        # inFile
        inLabel = Tkinter.Label(root, text='plist file (in):')
        inLabel.grid(column=0, row=0)
        # grabbable entry field
        self.inFileBox = Tkinter.Entry(root, width=30)
        self.inFileBox.grid(column=1, row=0)
        # outFile
        outLabel = Tkinter.Label(root, text='JSON file (out):')
        outLabel.grid(column=0, row=1)
        # grabbable entry field
        self.outFileBox = Tkinter.Entry(root, width=30)
        self.outFileBox.grid(column=1, row=1)
        # Button to grab fields
        convertButton = Tkinter.Button(root, text='Convert',
                                      command=self.makeConversion)
        convertButton.grid(column=0, row=3)
        # A quit button
        quitButton = Tkinter.Button(root, text='Quit',
                                    command=self.onExit)
        quitButton.grid(column=1, row=3)
        root.mainloop()

    def onExit(self):
        self.root.quit()

    def makeConversion(self):
        """ grab the configuration values, convert, and write """
        inFile = self.inFileBox.get()
        outFile = self.outFileBox.get()

        plist = open(inFile,"r").read()
        theData = StringIO.StringIO(plist)
        plist_dict = readPlist(theData)
        open(outFile,"w").write(json.dumps(plist_dict))

Converter()

Download it:

plist-to-json.py (zip file, ~4KB)

Posted in Uncategorized | 2 Comments

Python 2.7 and XCode 4

Here’s a relevant link for setting up a project (I’m using it for cross-platform development, not PyObj-C): Python + XCode @ SO

For debugging you’ll probably have to go outside XCode, or figure out how to set Python debugging up properly. Supposedly LLDB has support, but in XCode you’ll get SIGTRAP when you run your program. Personally I think I’ll debug outside XCode, then figure out how to set up LLDB+Py+XCode4 if and only if I have so much debugging that running from another environment becomes a chore.

Posted in Uncategorized | 1 Comment