What the World Needs…

This is a helpful application that doesn’t exist yet, that I know of.

It works inside Mail. It lets you select an email message, or text inside an email message, select something from a contextual menu, and have your Address Book automatically updated with the phone and address in that email or text.

Even better, possibly, is an application that can scan all your emails and find the ones with text that looks like contact information (numbers formatted like phone numbers, and “Street” or “Drive” or variants). It maps the sender addresses to your Address Book entries, and offers to change them all en masse.

Even better than that would be an application that, in addition, does this when you first receive email, and makes the changes semi-automatically. By “semi-” I mean it presents you with exactly what information it’s going to change first, and allows you to edit what changes it makes or cancel them individually. (Something I’d really like to see more of in Sync Services, by the way.)

Time and time again, I look up someone’s contact information in Address Book, and it’s outdated. They’ve sent me an email with the new information, so I have to hunt for it, and do the tedious cut-and-paste from one application to another.

I would pay for this application.

Better make it fast, though; sounds like Audigone material.

I’ve Been Moved! Groups & Files Inadequacies and Subversion

The reorganization of source files and their enclosing directories in large commercial projects tends to be nasty, in my experience.

1) On Macs at least, they use CVS as their source code management (SCM) system. CVS can’t handle moving files and folder gracefully. At best, you delete the files in one place and check them in somewhere else, which abandons their history in the original location. And you can’t delete directories at all. Instead, you leave the old, dead, empty directories there and instruct everyone to use -P when they do their checkouts and updates, so that empty directories are pruned for local repositories.

2) The major IDEs on the platform treat the visual representation of the Groups & Files in your project as something entirely different than the actual files and directories on disk.

“Groups” (yellow folders) in Xcode are only meaningful as an in-project organizing principle. Moving them, or the file representations within them, around in your project window, won’t change what’s on disk.

And conversely, if you move files and directories around on disk, the project won’t automatically be updated to the new arrangement.

So for a reorganization, after you move everything around on disk, you can look forward to doing the exact same thing again in your IDE user interface. This, as you can imagine from how I’m describing it, frustrates me to no end. But it gets worse.

For newer projects, you can fix 1) by switching to Subversion, where both files and directories can be moved around easily with complete retention of their history. But you can’t somehow execute the moving around Subversion commands in the Xcode UI itself, because of 2).

Why did anyone think keeping Groups & Files completely unrelated to disk directories and files was a good idea? Every commercial project I’ve ever worked on has made its Groups & Files tree mirror the on-disk directory structure whenever possible – the only times they diverged was due to maintenance error.

The only good reason I’ve had for a different Groups & Files structure was for a library where all the library headers needed to be available in the same top-level directory. So on disk, it was an undifferentiated list, but I used a 3-4 level deep group hierarchy in the project itself to be able to organize the files better conceptually. But, as I said, I’ve never seen this in the wild.

I’ve just seen hours upon hours spent maintaining hierarchies in two places, both for project creation and the inevitable reorganizations that followed.

Upgrading the Omni Frameworks for Xcode 2.1

Last time I talked about the Omni frameworks, it was to warn you to use the .pbproj versions, instead of the more logically-named .xcode versions. That was all I needed to do to make them work with Mac OS X 10.3 “Panther.”

Now we’re up to Mac OS X 10.4 “Tiger” and Xcode 2.1. Is it more complicated this time? You bet.

I use cross-project references to refer to the Omni projects in my own project. Important tip: cross-project references only work in Xcode 2.1 if all projects have been upgraded to 2.1 project format. So I upgraded all three projects. Since I used the new .xcodeproj suffix for the upgraded projects, that meant I had to remove the old project references from my project and add the new ones, which meant I had to re-add all the dependencies and build products for my project’s targets. A bit of a pain.

Once I’d finished that, OmniBase built fine. OmniFoundation did not.

The OmniFoundation project refers to /usr/lib/libbz2.a, which is missing under Tiger, replaced by /usr/lib/libbz2.dylib. I don’t want the project to refer to the dynamic version of the library: that would presumably make it only work under Tiger. I want it to use the static version of the library.

For the C++ standard library, you can switch from the dynamic version (available 10.3.9 and up) to the static version (works in 10.3.8 and lower) by switching compilers. GCC 3.3 uses the static library, GCC 4.0 uses the dynamic library. This is why just changing the SDK from 10.4.0 to 10.3.9 (or even 10.2.8) isn’t enough if you want to support older versions of the OS.

Changing compilers doesn’t help with the bz2 library, however; instead, the SDK is the key here. The full static library is still available on a Tiger system, but not under /usr/lib. Instead, it’s available under /Developer/SDKs/MacOSX10.3.9.sdk/usr/lib. So I changed the project to refer to that.

There were a few other tweaks needed. I went into the OmniFoundation (Framework) JAM-based target and both unchecked the “Treat all warnings as errors” checkbox and, under the Expert View, removed -Werror from the WARNING_CFLAGS setting. Actually, first, I tried going in and fixing all the warnings, but some of them turned out to be quite obscure, so I finally gave up.

I had to follow the same steps for the OmniAppKit (Framework) target in the OmniAppKit project.

Could it be dangerous to let so many warnings go by? Maybe. But I hadn’t changed the code to produce the warnings; instead, they occurred because GCC 4.0 is more strict and produces more warnings than GCC 3.3. Should someone fix them eventually? Yep. For tonight, though, it’s good enough that all the Omni frameworks I have build successfully.

Finally, a note about how Xcode 2.1 builds targets referred to via cross-project references. Before, Xcode would build the targets in other projects without any build style at all. In 2.1, Xcode attempts to match build configuration names. If your project is building with the configuration “Development,” and the other project has a configuration named “Development,” it is used for the other project’s target, too. It’s a very nice improvement.

New Linked Blogs!

I’m adding a couple of developer blogs to my list:

Theobroma Cacao, by Scott Stevenson. At first glance, I thought the blogger’s name might be “Theobroma Cacao,” but that’s just because I didn’t know that it’s the Latin name for the plant from which chocolate is made. Mmm, chocolate. He has a bunch of posts about WWDC 2005, though, to be fair, no shirt pictures.

Xcode Experiences, by Marshall Clow, his blog about moving from CodeWarrior to Xcode, since CodeWarrior will not be supporting the Universal Binary format required to run on Intel Macs. Marshall’s blog was the impetus for my last post about CodeWarrior and Xcode.

Ridiculous Fish, by Peter Ammon, an AppKit developer. Buzz Andersen, also on my list, introduces Peter’s blog here.

Though Buzz also seems to have changed his RSS feed URL sometime in the last 3 months, from http://www.scifihifi.com/?flav=rss to http://weblog.scifihifi.com/feed/, which caused my NetNewsWire feed of his blog to go dead. Bad Buzz!

Welcome, everybody!

Targets (and More!) in CodeWarrior vs. Xcode

I opened up CodeWarrior 8.3 again for the first time in a while, in order to talk about targets in CodeWarrior vs. targets in Xcode (see below).

Instant opening and editing of huge source code files! Cmd-tab, instead of the vastly more cumbersome Cmd-Opt-Up Arrow! Multiple versions of the tools on the same partition!


Sorry, nostalgia got the better of me. Onward….

CodeWarrior 8.3 on Tiger

CodeWarrior 8’s last update was late 2002, and I’m on Mac OS X 10.4 “Tiger,” which (if you didn’t hear) was released this year, so of course I was expecting problems.

Here are the steps I used to get something up and running:

1) In CodeWarrior’s application-wide IDE preferences, under General -> Source Trees, change the OS X Volume path from / to /Developer/SDKs/MacOSX10.2.8.sdk. Be sure to save your changes before opening any projects.

2) Open Metrowerks CodeWarrior 8.0/Metrowerks CodeWarrior/MacOS X Support/CocoaHeaders/CocoaHeaders.mcp and rebuild all targets.

3) Create a new CW project, based on the Mac OS X Cocoa Stationary.

4) Build and run/debug. Don’t close CodeWarrior.

Importing a CodeWarrior Project into Xcode

Now, I take this working CodeWarrior project over to Xcode:

1) Import the CodeWarrior project into Xcode. The Import command is under the File menu. Don’t check the “Import Global Source Trees from CodeWarrior” checkbox.

There’s no step 2)!

Oh, wait, there is. Such as copying the info from the .plc file to an Info.plist file. But my goal here is not to get the project completely functional on Xcode. There are other places to go for that, such as Apple’s online document Porting CodeWarrior Projects to Xcode.

My goal is…well, first, in the interest of not throwing away useful information, I might as well list the problems I had during the import.

Problems During Import

  • On one machine I had, the Xcode importer had problems if the project to be imported was on my Desktop. If I moved it to another partition, it imported without errors.
  • On that same (cursed?) machine, I had a problem with Xcode not knowing where CodeWarrior was. Quitting and restarting Xcode didn’t solve the problem, but it worked correctly after the machine fell asleep and was woken up (??).

As with other Xcode issues, I would say keep fiddling with it, and you’ll probably get it to work.

Target, the Concept, in CodeWarrior and Xcode

My goal, as I started to say above, is to demonstrate the difference in the concept of target between Xcode and CodeWarrior.

Make an Xcode Cocoa Application project and set it next to the CodeWarrior import.

Xcode’s non-imported version has only one target, called whatever the project was originally named. The CW version has two targets, Cocoa Debug and Cocoa Final.

CodeWarrior handles the concepts of “debug” and “release” versions of your application by giving you two completely different targets. You have to add the proper files for compilation to each of those targets, and you have to specify all the settings, such as access paths and warnings, for each as well.

In Xcode, “debug” and “release” are just considered variants of the same target. All files are specified just once, in a single target. All settings which are not debug or release-specific can be set on that target as well. Then, the debug and release-specific stuff is set in the build configuration associated with that target.

This works in Xcode because you can easily set macros outside any source code files. You don’t need a separate prefix file to set values like DEBUG for debug versus release, just set a build setting in each of your “debug” and “release” build configurations.

This didn’t work optimally in Xcode, up until 2.1, because these variants used to be built in the same location. In CodeWarrior, the result of the “debug” and “release” targets usually have different names, and different temp file locations. In Xcode? Same name, same temp file locations. So you generally had to wipe away the result of one configuration to build the other. This has been fixed in 2.1. (Though for some people the “fix” broke behavior that they depended on.)

Getting All Shirty

When I first created this blog, I didn’t work for Apple, and Mac OS X 10.4’s codename, “Tiger,” hadn’t yet been announced.

So when it was, I prided myself on being ahead of the curve. Perhaps…evening inventing the curve?

Now, at WWDC, my prescience has once again been demonstrated for all the world to see:

Very orange t-shirt with white WWDC2005 text

Apple even borrows my blog background for such important things as its engineering shirt color.

Next thing you know, they’ll have an application called “Help”….

Subversion Conversion: Upgrading Projects to Xcode 2.1

(See bottom for updates.)

You’ve followed my Subversion posts so far; you have an Xcode 1.* or 2.0 project you’ve checked into your Subversion repository.

Now, you’ve updated to Xcode 2.1, and you want to open your .xcode project.

In previous versions of Xcode, the application allowed you to update your project in-place, which made source control maintenance easy. But now, Xcode will prompt you to “Upgrade a Copy,” and will require you to use a new project suffix, .xcodeproj.

Xcode projects are really folders, a.k.a. bundles. So a project name change means a folder name change. In CVS, this is suboptimal. In Subversion, not so much, but Xcode’s upgrade process complicates matters. Here are the steps that I used:

1) Open the project in Xcode 2.1. Click the “Upgrade a copy” button, and choose a temporary project name, like Temp.xcodeproj.

2) Go to Terminal, type in svn rename MyProject.xcode MyProject.xcodeproj and then svn commit -m "My message" MyProject.xcode MyProject.xcodeproj, where “MyProject” is the actual name of your project, and “My message” is your commit message.

You may need to use svn revert MyProject.xcode/* first to make sure any trivial project changes made during your last 2.0/1.* session, but after your last commit, don’t prevent the rename.

3) Copy all the gunk inside the Temp.xcodeproj bundle to the renamed project bundle. The most important thing will be the project.pbxproj, but there will be other files that start with your or other people’s username and end in various suffixes that you can copy and commit at your discretion.

4) Open MyProject.xcodeproj again. Now, from within Xcode itself, you’ll be able to do the rest of your Subversion commits, namely the project.pbxproj and other myusername.* files. This is most easily done from the SCM smartgroup visible under Groups & Files in the Default and All-in-One Xcode layouts. Select the files, then Control-click them and choose “Commit Changes…” from the contextual menu.

You couldn’t commit them from within Xcode before because you didn’t have the proper .svn folder in the same place as the changed files.

Basically, Xcode wants to be in charge of the project rename, but Subversion also wants to be in charge of the project rename. To satisfy both, you have to do it twice, and then do your own manual (but simple) “merge”.

And you will have to do this for every Xcode project in your Subversion repositories.

The good news is that, once you’re done, your project history will remain uninterrupted.

Update #1: One thing that doesn’t work is changing the suffix to .xcodeproj first and then opening the project in Xcode 2.1. The Xcode UI still requires you to upgrade a copy; it will still not upgrade the project in-place.

Update #2: Another way to do this is to skip 2) completely. The resulting MyProject.xcode will still open in Xcode 2.1 fine, and you won’t have to worry about renames in your repository.

The Xcode 2.1 UI doesn’t give you the choice to use the .xcode suffix for the upgraded project, but the fact is all historical suffixes are still valid for 2.1 projects, even .pbproj and .pbxproj. Xcode examines the actual contents of a project to determine whether it needs to be upgraded, not its suffix.

The Restaurant at the End of the…First Day of WWDC

I’m bad with names, but here’s a list of the people I remember talking to at any length tonight at the WWDC 2005 Weblogger Dinner, or at least those that have weblogs/Web pages:

Please add your name in the comments if I’ve forgotten you. Or let me know if you find your way here and think, “Huh? I never met this guy!”

It was a fun evening. Yummy food. The venue was packed for the entire time I was there.

Update #1: So of course I forget the person mentioned in my previous post!

Subversion Dispersion: Searching “Tiger”+“Subversion”

If I’m remembering it correctly, Luis de la Rosa, whom I met at the WWDC 2005 Weblogger Dinner tonight, mentioned how, when he searched on “Tiger” and “Subversion” in Google, instead of getting Apple documentation on using Subversion with Mac OS X 10.4 “Tiger,” he got…me!

Aww! You like me, you really really like me!

Or, y’know, maybe not. So for those of you coming from Google (hi!), here’s a link to the very helpful Xcode 2.1 User Guide chapter on using Subversion with Mac OS X 10.4 “Tiger”.