Tuesday, August 4, 2009

Configuring a Wireless Bridge Using Two Apple Airport Expresses

Here's the scenario: You want to setup a wireless network, and you also need to connect a non-WiFi network device to your new wireless network. E.g. you're setting up a wireless network at work, and you've got a network printer that only has ethernet, no WiFi, that you want to connect to your network. For the purpose of this exercise, we'll use this scenario to explain the setup.

Step 1. Buy Two Airport Expresses. I recommend these because they are easy to setup, they work great, and the design is ingenious (it's about the size of your standard wall plug). If you don't have any ethernet cable, you'll need to buy at least one, maybe two ethernet cables. One will go from the cable/dsl modem to an airport express, the other will connect your printer to the second airport.

Optionally: You may want to buy the more expensive Airport Extremes instead of the Expresses, in the event that you want more ethernet ports available. But you can always add on a cheap switch later if you need more ports on an Airport Express.

Step 2. Unwrap both devices, and mark them to keep them straight. Put a sticker or mark one with a Sharpie so you can tell them apart. One of these will be the heart of your wifi network, the one every device connects to -- we'll call this Airport A. It will be connected to your cable/dsl modem.

The other will be connected to your non-Wifi device (e.g. your printer), allowing it to connect to Airport A and the Internet... we'll call this one Airport B.

Step 3. Plug Airport A into power. Plug it into the wall near your cable/dsl modem. You'll see an amber light blinking on the Airport, this is normal.

Step 4. Insert the Airport Express setup CD into your computer, and run the software. After a minute you should see an Airport available named "Base Station xxxxxx," where xxxxxx will be a series of letters and numbers. Select this, and press the Continue button to configure it.

Step 5. Configure Airport A.

You'll have a few options to fill in now:

  • AirPort Express Name: You can name it anything you want, such as Airport A.
  • AirPort Express Password: This is a password on the device you'll need whenever you want to re-configure the Airport Express. You will not be sharing this with others.
  • Select what you want to do with Airport Express: Choose "I want to create a new wireless network."
Continue to the next screen:
  • Wireless Network Name: This is different from above. Other people will use this to identify your WiFi network if you want them to connect to it. (And, hey, maybe even when you don't want them to connect to it?!)
  • WPA/WPA2 Personal: Choose this option and enter a password you will be comfortable giving to your guests to use your WiFi network. For strong security, this should be different from the password you chose on the previous screen. You wouldn't want your guests to be able to re-configure your Airport Express.
Continue to the next screen:
  • Select how you connect to the Internet. For this example, you'll choose the first option, "I use a DSL or cable modem with a static IP address or DHCP."
Continue past the next screen, "Using DHCP," is the normal option for most people. Your ISP will send information to the Airport Express to connect it to the internet using this setting.

Continue to the next screen and after reviewing your choices, press "Update."

The on-screen options should prompt you to finish and allow Airport A to restart if necessary. You should also restart your cable/dsl modem at this time.

You can now connect to the internet by connecting your computers to Airport A.

Step 6. Plug Airport B into power. Plug it into the wall near your printer. You'll see an amber light blinking the Airport, this is normal.

Step 7. Restart the Airport Utility software. If you don't see the new "Base Station xxxxxx" appear, go ahead and restart the Airport Utility software. Within a minute you should see it appear on the left side. Select it and continue on to configure it.

Step 8. Configure Airport B.

You'll have a few options to fill in now:
  • AirPort Express Name: You can name it anything you want, such as Airport B.
  • AirPort Express Password: This is a password on the device you'll need whenever you want to re-configure the Airport Express. You will not be sharing this with others. You should choose the same password as you chose above (not your WiFi password, but the first password you chose for the device configuration), just to keep them straight.
  • Select what you want to do with Airport Express: Choose "I want AirPort Express to join my current network."
Continue to the next screen:

  • Select what you want to do with AirPort Express: Choose "I want Airport Express to wirelessly join my current network."
Continue to the next screen:
  • Wireless Network Name: Enter the Wireless Network name you chose for Airport A here. This is the WiFi network that Airport B will connect to, wirelessly.
  • Wireless Security: Choose "WPA/WPA2 Personal."
  • Wireless Password: Enter the same Wireless Network password you chose above for Airport A's WiFi network. (The password you established to give out to your guests.)
Continue to the next screen and after reviewing your choices, press "Update."

The on-screen options should prompt you to finish and allow Airport A to restart if necessary.

Step 9. Connect Airport B to your printer with an ethernet cable. Follow your printer's instructions for setting up your network connectivity on the printer. When prompted, select "DHCP" and not static IP address.

Step 10. You're done.

Extremely Fast Luhn Function for C# (Credit Card Validation)

If you want to validate that a credit card number is valid, you need to use the Luhn algorithm. It uses the last digit in the card number and calculates a checksum to ensure the number is valid. (Obviously this doesn't ensure that the card actually works, only that the number seems real.)

Everyone and their mother has posted a .NET/C# version of Luhn, but they were all really drawn out and slow. I initially settled on this one by Paul Ingles hosted on CodeProject., since at least his code was commented and readable. I shortened it up and eliminated some blocks of code and variables, making it easier for me to follow, but without any change in performance. Then I swapped in some tricks to speed it up about 4x (cast char to int and subtract 48 to get the integer version of a number that starts as a char string).

I felt this was good enough, but then I stumbled upon this pseudo code for Luhn algorithm by Cliff L. Biffle. Not only is it much, much shorter, but it was about another 8x faster than my code! I went from validating 100,000 numbers in 550ms to 100,000 in 15ms, a 37x speed increase!

I wrote a C# function implementing the pseudocode, and here it is below.


/// Extremely fast Luhn algorithm implementation, based on
/// pseudo code from Cliff L. Biffle (http://microcoder.livejournal.com/17175.html)
///
/// Copyleft Thomas @ Orb of Knowledge:
/// http://orb-of-knowledge.blogspot.com/2009/08/extremely-fast-luhn-function-for-c.html

///

private static bool IsValidNumber(string number)
{
int[] DELTAS = new int[] { 0, 1, 2, 3, 4, -4, -3, -2, -1, 0 };
int checksum = 0;
char[] chars = number.ToCharArray();
for (int i = chars.Length - 1; i > -1; i--)
{
int j = ((int)chars[i]) - 48;
checksum += j;
if (((i - chars.Length) % 2) == 0)
checksum += DELTAS[j];
}

return ((checksum % 10) == 0);
}

That's it!

Monday, October 20, 2008

Strange Behavior When Your .NET Application Uses ActiveX/COM and Data Execution Prevention (DEP) is Enabled?

This issue was extremely obscure, but I wanted to document it anyway. The moral of the story is, if your .NET application is using an ActiveX/COM object, and is behaving strangely on Vista with DEP enabled, try to get DEP turned off and see if anything changes. In our case, a third party ActiveX/COM object was trying to pop up a window, and DEP was killing it, causing strange behavior in the application we were debugging.

Details...

We've got a MagTek MICRImage check reader, and we've written a program in .NET that communicates with it, and everything works fine. We are using SaxComm8.ocx to communicate with the reader (an ActiveX object that is using AxInterop for .NET use).

Next thing you know, we are trying to debug the application, and the checkreader no longer triggers any "check read" events when you scan a check. Communication otherwise works fine with the reader. We'd checked everything to do with your serial ports.

In our case, it turns out it was a combination of the SaxComm8.ocx code being overwritten by a previous version we had that was a trial only. Typically this trial version pops up a warning box about the trial period. But in Vista with DEP running, this dialog was never appearing. Most likely this was then causing the SaxComm8 object to go into a weird state, no longer communicating with the reader.

Finally found that DEP was causing the problem. Then I discovered Vista would not allow me to disable DEP for this app (WHY?!). Used the command bcdedit /set nx AlwaysOff, and restarted. Of course, now DEP is totally disabled, but finally I was able to see the trial notice popup and realize what was happening.

Once I overwrote all trial copies of the .ocx file, I did a regsvr32 /u saxcomm8.ocx to unregister it, and a regsvr32 saxcomm8.ocx, to register it, and now everything works!

Wednesday, September 3, 2008

Unable to Install Update for Office 2008 for Mac

If you are trying to install an update for Office 2008 for Mac, and you're getting an error that says, "A version of the software required to install this update was not found on this volume," keep reading for a possible solution that worked for us....

We had installed Office 2008 for Mac fresh on an iMac with Mac OS X 10.5.4. We then ran auto update, and 12.1.1 updater ran successfully and patched Office. We then ran auto updater again, and it wanted to patch to 12.1.2. This FAILED indicating no volume could be found running the appropriate version, similar to this:



We did the steps below and it worked:

  1. Download the update from MacTopia, instead of letting the Microsoft AutoUpdater download it.
  2. Once the .dmg file is downloaded and mounts as a virtual disk, copy the updater software from the virtual disk over to your desktop, and unmount the virtual disk.
  3. OPTIONALLY: Temporarily run as an Administrator account, if possible... (this worked for me)
  4. OPTIONALLY: Run Disk Utility and fix permissions on your disk.
  5. OPTIONALLY: Reboot.
  6. Run the updater software directly from your desktop. It should work.
You can skip over the steps 3, 4, and 5 if you want to try your luck, but if it doesn't work, try it again doing those optional steps.

Wednesday, March 26, 2008

Triggering Events on page load (and right before)

  1. Use prototype.js in your page.

  2. Call the Prototype function Event.observe() for the 'load' event. You can call the Event.observe() function as many times as you want, it will simply append your code each time, so as not to clobber each other when the event is fired. There are two ways you might perform this call. If you have a function you want to run, simply call:

    Event.observe(window, 'load', yourFunctionName);

    If you have a bit of code you want to run, call this instead:

    Event.observe(window, 'load', function() {
    // your bit of code here
    });
Do you want it to run onLoad... or onDOMLoad?

One important thing to realize is that the 'load' event for a page only fires AFTER all images on the page have been loaded. This may take a while, depending on your page design. You may be thinking that you will just run your bit of code when the page first starts loading. The problem with that is the DOM is not completely available yet, so your code will usually fail.

This guy has some javascript code that allows you to basically "observe" the onDOMLoad event, even in browsers that don't really export such an event. If you use his code to attach code to this event, it will run after the DOM is available, but before the "onload" event is fired for the page body.

The downside is it doesn't use prototype.js, so it may actually overlap a bit of that functionality. However, as of Prototype.js 1.6, their site was actually pointing to people to this guy's examples, so presumably that means there is no current expectation that Prototype does or will offer similar functionality.

Wednesday, November 14, 2007

System.Drawing.Image.Save() results in ArgumentException: "Parameter is not valid"

If you are using the .NET Image.Save() method to save an image, and you receive an ArgumentException with the message "Parameter is not valid," you probably spent a while examining the parameters you were passing into the Save() call, right? You probably banged your head against the wall and said, "Dear GOD, please tell me WHICH PARAMETER is not valid!"

Unfortunately, the error message is completely unhelpful, and you are seeing it because you had a brain fart. You have called Dispose() on the image object before you tried to Save() it.

If this helps you, please comment on this post, thanks.

Friday, November 2, 2007

Google Maps GIcon imageMap Property

Been fooling around with Google Maps API lately. When using custom markers on the maps, you should specify the imageMap property, so that the markers are still clickable even when beneath a "shadow," in Firefox. Yet the Google Maps API never describes the format in detail, simply stating it is "an array of integers representing the x/y coordinates of the image map we should use to specify the clickable part of the icon image in browsers other than Internet Explorer."

I searched high and low and could not find anyone that explained the format in more detail, but after studying the HTML image map formats, it became clearer that Google wants you to use the same format for this imagemap array as the "polygon" type of imagemap that HTML uses.

Specifically, your x,y pairs should denote points OUTLINING the area you want to be clickable. In very simple terms, if you have a square icon that is 8x8, and you wanted the entire square to be clickable, you would use an array of: [0,0, 7,0, 7,7, 0,7]. The first pair is the top/left corner, the second pair is top/right, the third is bottom/right, and the fourth is bottom/left.

They key is to think of your starting point, and traveling from point to point in order, encircling the area to make clickable for your GIcon (aka google.maps.Icon).