Friday, November 14, 2014

How to Solve Mac Pro Problems on Boot (HDMI and Display Port Display Problems and Yosemite Upgrade)

How to fix two problems our team has had with the Mac Pro (2014):
  • We had a wierd display issue causing a lock-up (or freeze) on boot. We found out this was caused by connecting to two monitors via HDMI and display port. By getting another display port cable and connecting to both display via display port, all works great. (Note: the genius bar took a look and had said that the Mac Pro was a niche product of Apple and that it would probably take a long time to work out what the issue causing this was, etc.)
  • We had a computer that on boot on start of Mavericks to Yosemite upgrade would show a grey screen for 10 minutes and then the apple and then a few minutes later would reboot, and would continue to do this. Attempting to use shift (safe mode boo), zapping PRAM, and recovery boot (command-R) did not work. We noticed when using command-v (thanks to Tommy for remembering that) we could see it was stuck after showing the second period of efi in verbose mode). A co-worker had a long support call with Apple and they gave up and directed him to a local Apple affiliate for support. We determined this was caused by using the USB output of a Dell monitor (which had a built-in USB hub to allow for Bluetooth peripherals- a keyboard and mouse). Unplugging everything except the monitor and using a wired keyboard and switching the port that was used for display port fixed this problem and allowed it to continue (start) the upgrade process.

Wednesday, October 22, 2014

Git Hooks: One Size Unfortunately Does Not Fit All

Was disheartened to find out recently that despite all the progress in the world's software development community, even when everyone is using git, you cannot rely on a standard set of hooks to enforce commit rules and perform other actions.

Some links to show what I'm talking about:

The problem isn't that something like hooks can't be accomplished across IDEs and platforms in 2014, but rather that it is a pain. Hooks shouldn't require this much lock-in.

Wednesday, October 15, 2014

Which Programming Language or Architecture Is Most Popular?

Although my favorite way of judging programming language or architecture popularity is indeed.com's trends, it might also be helpful to take a look at Tiobe's stats. Other gauges include GitHub's trending projects and architectures and programming language showcase.

Also, here's a mid-2014 post that analyzes GitHub, showing trends in language usage, and another showing Javascript framework popularity.

Saturday, September 20, 2014

Should I Get the 2 Large or the 3 Medium Pizza Special from Papa John's?

As of 2014, the Papa John's large pizza is 14 inches and the medium is 12 inches. They have a special running for 2 large or 3 medium, and if you're only concerned about the size without the crust that is ~11 inches diameter for the medium or ~13 in for the large.

3 medium = 3 x 95.03 = 285.09 sq. in.

2 large = 2 x 132.73 = 265.46 sq. in.

So, the medium is the better deal for the same price. However, the large special included a specialty pizza, so that's what I got.

Friday, September 12, 2014

Java Fun

It's Friday as I'm writing this, so for fun, here are some neat facts about Java.

  • hashCode() of strings are a hash int value of the contents of the string which can be 0 or at the integer limits.
  • Math.abs(Integer.MIN_VALUE) == Integer.MIN_VALUE
For some information about hashCode() strings, see this answer in StackOverflow.

Some examples in beanshell:

% System.out.println("actuation conjugant".hashCode());
2147483647
% System.out.println("bequirtle zorillo".hashCode());
0
% System.out.println("polygenelubricants".hashCode());
-2147483648
% System.out.println(Integer.MIN_VALUE);
-2147483648
% System.out.println(Math.abs("polygenelubricants".hashCode()));
-2147483648

I quickly hacked up a simple Java app to process OS X's /usr/share/dict/words. It's suboptimal but works for a test:

import java.io.*;
import java.util.ArrayList;

public class Test {
    public static final void main(String args[]) throws IOException {
        ArrayList words = new ArrayList();
        try(BufferedReader br = new BufferedReader(new FileReader("words"))) {
            for(String line; (line = br.readLine()) != null; ) {
                words.add(line);
            }
        }

        String s;
        for (int i = 0; i < words.size(); i++) {
            s = words.get(i);
            test(s);
            test(s.toUpperCase());
            test(s.toLowerCase());
            for (int j = 0; j < words.size(); j++) {
                s = words.get(i) + words.get(j);
                test(s);
                test(s.toUpperCase());
                test(s.toLowerCase());
                s = words.get(i) + " " + words.get(j);
                test(s);
                test(s.toUpperCase());
                test(s.toLowerCase());
            }
        }
    }

    public static final void test(String s) {
        int h = s.hashCode();
        if (h == Integer.MIN_VALUE || h == 0 || h == Integer.MAX_VALUE) {
            System.out.println("" + h + " = " + s);
        }
    }
}

Some strings with hashCode() of Integer.MAX_VALUE, 2147483647 (some of the following I found with a different version of the code):

ABASEDNESS RESEMBLANCERESEMBLANT
actuation conjugant
addlepate Burushaski
actuation conjugant
addlepate Burushaski
AIRCREWBRUTALIZATION
ANALYZATIONDIANCECHT
andrewsite sruti
apatetic libber
attached retranslate

Some strings with hashCode() of 0:

accismus toddlertoddy
acephalisthematolysis
ACETOMORPHINE ACHENE
acousmatic gymnarchidaegymnarchus
ALVEOLODENTAL WALDENSES
APODAN UNCONTENDED
auraadmonitorial
BALSAMROOT SQUARENESS

Some strings with hashCode() of Integer.MIN_VALUE, -2147483648:

accompt hypercriticism
acetothienoneruledom
achroite unenviablyunenvied
adventitiouslyoniscoidea
AFFORCEMISBAPTIZE
aggressquadrifurcate
bamboozlercastaway

I modified it to wait until the end to output and show progress, e.g.

rate = 186ms/word set. Estimated 730 min left. 1 found
Here's the code with the modification:

import java.io.*;
import java.util.ArrayList;

public class Test {
    public static final void main(String args[]) throws IOException {
        ArrayList<String> words = new ArrayList<String>();
        try(BufferedReader br = new BufferedReader(new FileReader("words"))) {
            for(String line; (line = br.readLine()) != null; ) {
                words.add(line);
            }
        }

        String s;
        int counter = 0;
        ArrayList<String> results = new ArrayList<String>();
        long startTime = System.currentTimeMillis();
        for (int i = 0; i < words.size(); i++) {
            s = words.get(i);
            test(s, results);
            test(s.toUpperCase(), results);
            test(s.toLowerCase(), results);
            for (int j = 0; j < words.size(); j++) {
                s = s + words.get(j);
                test(s.toUpperCase(), results);
                test(s.toLowerCase(), results);
                s = words.get(i) + " " + words.get(j);
                test(s.toUpperCase(), results);
                test(s.toLowerCase(), results);
            }
            counter++;
            long rate = (System.currentTimeMillis() - startTime) / counter;
            long minLeft = ((words.size() - counter) * rate) / 1000 / 60;
            System.out.println("rate = " + rate + "ms/word set. Estimated " + minLeft + " min left. " + results.size() + " found");
        }
    }

    public static final void test(String s, ArrayList<String> results) {
        int h = s.hashCode();
        if (h == Integer.MIN_VALUE || h == 0 || h == Integer.MAX_VALUE) {
            results.add("" + h + " = " + s);
        }
    }
}

Then I made it multi-threaded which helped it to go a bit faster:

rate = 86ms/word set. Estimated 337 min left. 0 found
Here's the code with the suboptimal multi-threading modifications:

import java.io.*;
import java.util.ArrayList;

public class Test {
    public static final int SPLIT = 3;
    public long startTime;
    public int counter;
    public ArrayList<String> results;

    public static final void main(String args[]) throws IOException, InterruptedException {
        (new Test()).test();
    }

    public void test() throws IOException, InterruptedException {
        processWords(readWords());
    }

    private ArrayList<String> readWords() throws IOException {
        System.out.println("Reading file 'words'");
        ArrayList<String> allWords = new ArrayList<String>();
        try(BufferedReader br = new BufferedReader(new FileReader("words"))) {
            for(String line; (line = br.readLine()) != null; ) {
                allWords.add(line);
            }
        }
        return allWords;
    }

    private void processWords(ArrayList<String> allWords) throws InterruptedException {
        System.out.println("" + SPLIT + " threads starting");
        ArrayList<ArrayList<String>> wordLists = split(allWords, SPLIT);

        this.results = new ArrayList<String>();
        this.counter = 0;
        this.startTime = System.currentTimeMillis();

        for (ArrayList<String> words : wordLists) {
            (new Thread(new WordHashCodeChecker(words, allWords, this))).start();
        }
        
        while(counter < allWords.size()) {
            Thread.sleep(1000);
            if (counter > 0) {
                long rate = (System.currentTimeMillis() - this.startTime) / counter;
                long minLeft = ((allWords.size() - counter) * rate) / 1000 / 60;
                System.out.println("rate = " + rate + "ms/word set. Estimated " + minLeft + " min left. " + this.results.size() + " found");
            }
        }

        for (String result : results) {
            System.out.println(result);
        }

    }

    public ArrayList<ArrayList<String>> split(ArrayList<String> originalList, int numLists) {
        int usualMaxSize = originalList.size() / numLists;
        ArrayList<ArrayList<String>> lists = new ArrayList<ArrayList<String>>();
        ArrayList<String> current = new ArrayList<String>();
        for (int i=0; i<originalList.size(); i++) {
            current.add(originalList.get(i));
            if (current.size() >= usualMaxSize && lists.size() < numLists) {
                lists.add(current);
                current = new ArrayList<String>();
            }
        }
        return lists;
    }

    class WordHashCodeChecker implements Runnable {
        
        ArrayList<String> words;
        ArrayList<String> allWords;
        Test test;

        public WordHashCodeChecker(ArrayList<String> words, ArrayList<String> allWords, Test test) {
            this.words = words;
            this.allWords = allWords;
            this.test = test;
        }

        public void run() {
            String s;
            for (int i = 0; i < words.size(); i++) {
                s = words.get(i);
                checkHashCode(s.toUpperCase());
                checkHashCode(s.toLowerCase());
                for (int j = 0; j < allWords.size(); j++) {
                    s = words.get(i) + allWords.get(j);
                    checkHashCode(s.toUpperCase());
                    checkHashCode(s.toLowerCase());
                    s = words.get(i) + " " + allWords.get(j);
                    checkHashCode(s.toUpperCase());
                    checkHashCode(s.toLowerCase());
                }
                this.test.counter++;
            }
        }

        public final void checkHashCode(String s) {
         int h = s.hashCode();
            if (h == Integer.MIN_VALUE || h == 0 || h == Integer.MAX_VALUE) {
                this.test.results.add("" + h + " = " + s);
            }
        }
    }
}

Friday, August 29, 2014

Buying and Using a Used Verizon Phone

To buy a used Verizon phone, you first want to find a vendor. You could use a directory and intermediary service like Swappa. Swappa basically provides a directory listing and they ask the seller to try to ensure the phone is clean before sale. However, it does not absolve you from needing to ask that the phone has a non-zero and clean (not reported stolen) IMEI and is able to be activated on the Verizon network without additional work. If the phone is rooted be very careful, as it might have an IMEI of 0, which will be a problem. If you decide to go forward with the purchase, Swappa charges the buyer a certain amount (e.g. $10) as part of the sale as well as charging you from the seller the remaining amount of the sale, such that on your Paypal bill you would see the bill for Swappa and the charge from the seller. You can track the device during shipping and when you receive it, you must first check the IMEI to ensure it is not 0, and then try activating it. If you have any problem with your device don't mark the device as received; you would then need to comment on the sale page and then manually send a note in the resolution area of Paypal against the Seller (not Swappa) stating that the seller needs to reimburse you because you are sending the phone back, and then Swapper and seller must then credit you that amount they charged back. So, what Swappa really is doing here is just acting as a directory service and arbitrator for the sale. If you'd rather, you could try buying the phone on eBay or Craiglist, etc. If you do that, take the same precautions asking the seller if the device has a clean, non-zero IMEI that can be used on the Verizon network (e.g. CDMA, 3G (old/slow) or 4G LTE). You may need to go get a new SIM card from Verizon in order to activate your device. Unfortunately for the hearing impaired or those using chat, the Verizon chat support cannot help to the same extent that the phone support staff can, and they are much slower. Newer 4G LTE Verizon devices can automatically register on the network as part of the process, though you may have to reset your network settings on some devices if you are doing something like changing the phone number associated with the SIM. SIMs can vary in size! Older devices will need to call *228 to register on the Verizon network. This involves having to enter "1" on the phone to register after it is answered. The old device must either be off or the battery or even the SIM removed if the phone cannot be turned off (if the screen is badly damaged). To ensure your new device is both registered and able to use the Verizon network, you can call #832. I do not work for Verizon, so don't ask me questions in the comments- just call Verizon for assistance. Good luck!

Tuesday, August 26, 2014

Newer Workaround for set -e Bug in bash with RVM

Just found out that with the newer RVM (noticed in v1.25.28 and 29 (stable) but not sure which versions are affected), the old fix that we used in our bash script:

# Load RVM into a shell session *as a function*
if [[ -s "$HOME/.rvm/scripts/rvm" ]] ; then
  # First try to load from a user install
  source "$HOME/.rvm/scripts/rvm"
elif [[ -s "/usr/local/rvm/scripts/rvm" ]] ; then
  # Then try to load from a root install
  source "/usr/local/rvm/scripts/rvm"
else
  printf "ERROR: An RVM installation was not found.\n"
fi

That allowed use of so that RVM wouldn't break when using both set -e and cd'ing into a project directory that has a .ruby-version/.ruby-gemset:

set -e
cd /some/path/to/project

Will now break the script, exiting when you call the cd command (issue #3017).

The workaround provided by Michal Papis is to use the builtin cd and rvm use instead which seems to work:

set -e
builtin cd /some/path/to/project
rvm use .

Edited 2014-09-04 to provide solution from Michal Papis.