02
Mar 11

Updating UUIDs (the wrong way)

When you change an IDL interface, you have to update its uuid. Simple enough, just grab a new uuid and stick it in the .idl file. Easy enough, right?

I’ve been working on JSD (the JavaScript debugger interface) recently, and its IDL file contains 18 different interfaces. So say I add a method to jsdIScript. What interfaces do I need to update? From empirical observations (as in, when I forget to do one I get yelled at by a reviewer), you have to update the uuid on the interface containing any added methods, any interfaces that use that interface within their definitions, and any interface that… inherits? extends? that interface. Recursively.

Update: No you don’t, says #developers, though currently the conversation is not finished and it seems like it may come down to something of a judgement call (something like “if you modify the vtable, update the uuid. If you change an interface used in a method in such a way that it might break a user, update the uuid.”) I’ve updated my script to use the more common rule (inheritance only), though if you want the stricter behavior you can get it with –mode=params.

Leaving the rest of this post here for now:


Solution 1: Manually go through and trace the dependencies, updating uuids as you go.

Bleckth. Maybe someone else can manage to do that properly, but I’m an airhead, and I’d never get that exactly right.

Solution 2: Nuke ’em all and let God sort ’em out. (As in, update every single uuid in the file.)

Easy, but inelegant and I sometimes wonder if knowing whether an interface changed might actually matter to someone. Besides, this could result in me getting yelled at by a reviewer, and that’s what I depend on for figuring out the rules (see “empirical observations”, above.)

Solution 3: automate solution 1.

…so I did.

Give it a .idl file to chew on and one or more interfaces that you know you’ve changed, and it’ll chase through the dependencies for you. Assuming I got the rules right. It spits out a new file with brand-new uuids on all affected interfaces, and even spews to stderr the set of interfaces it’s updating and why:

% update-uuids jsdIDebuggerService.idl jsdIContext >/dev/null
uuids to update:
 jsdIContext because it was given on command line
   3e5c934d-6863-4d81-96f5-76a3b962fc2b -> 24ad10b2-8b4f-49f6-9236-f0ecaed0e19a
 jsdIStackFrame because its body contains jsdIContext
   7c95422c-7579-4a6f-8ef7-e5b391552ee5 -> 4c8c5902-77e8-4a9d-99f8-0ae6f0c58eec
 jsdIContextEnumerator because its body contains jsdIContext
   57d18286-550c-4ca9-ac33-56f12ebba91e -> d102ff63-59ea-4ed7-86d5-490c9e9b6b5a
 jsdICallHook because its body contains jsdIStackFrame
   3eff1314-7ae3-4cf8-833b-c33c24a55633 -> 150610f5-89cd-4f76-b960-06447471eb00
 jsdIExecutionHook because its body contains jsdIStackFrame
   3a722496-9d78-4f0a-a797-293d9e8cb8d2 -> cd3bfe98-c8a3-4c98-91d1-c7e2e79c396c
 jsdIDebuggerService because its body contains jsdIContextEnumerator
   aa232c7f-855f-4488-a92c-6f89adc668cc -> 75ab47da-2400-4efe-bb5e-745dceba4e06

(Sorry, no examples of inheritance-triggered changes there.)

It’s a quickie parse-with-regexes Perl hack.

One major flaw — it only considers a single .idl file. If some other .idl file depends on an interface modified within your file, then this won’t tell you it needs to be updated. I’m pretty sure that no other IDLs depend on the JSD IDL, so I don’t care yet. If this would be useful to you and that’s a necessary feature, let me know and I’ll throw it in. It’s easy enough to implement as long as you provide the list of IDL files to consider.

The other major flaw is that this doesn’t update the uuids in header files, once again because JSD didn’t need it. That would be some more work, and I don’t even know if I have the rules right so I’m not going to bother unless someone asks me to and tells me this is the right thing in the first place.

If nobody comments here within a week or so telling me I’m completely wrong about how this stuff works, I’ll add a link to this script on MDC. Maybe. If I remember. (And it turns out, someone did tell me I’m completely wrong. Yay!)