Both ears are now quite clearly up.

所有我感兴趣的资料,webdesign,webdev,linux,etc.Enjoy。
Both ears are now quite clearly up.

The Release Engineering:Future bugzilla component alternately inspires feelings of sadness, loathing, and contempt…and that’s just within the RelEng team!
I’m certain most developers first response to having their bug moved to the Future queue is, “Oh, look, my bug has fallen down a well.” Historically speaking, that may not be far from the truth.
Why does the Future component make people get punchy? For a long time, the Future component has lacked a decent description, so developers don’t know what it means when their bugs are moved there. Many have started hording their gigawatts in anticipation.
Bugzilla currently has the following small description of the Release Engineering:Future component:
“For longer term projects that have been agreed should be done, but have no immediate plans to so. These are not be part of the regular recurring triage. Advanced planning and placeholder goals for next quarter also go here.”
Despite the grammatical errors, this description is mostly accurate, but what does it actually mean:
Remember: this description is for the Future component ONLY. The RelEng team continues to pick up and work on bugs that need to get done on a daily basis.
I’m thinking about how to improve this description, and will get the description updated in Bugzilla once I have achieved some rough consensus. In the meantime, I’ve posted this description of the Future component in the wiki as an ongoing reference.
The (Ever-Increasing) NumbersAt the time of writing, the Release Engineering:Future component has 343 bugs in it. This number has grown steadily over the past year despite having more release engineers on staff, and having made a great many improvements to our release automation and our continuous integration infrastructure.
Our turnaround time for bugs in the Future component is also not stellar. At our urging, the Mozilla Metrics team recently started setting up a dashboard to give us various statistics on our Bugzilla usage. Bugs don’t get fixed in the Future queue, so it’s hard to make truly accurate assessments here, but there are a lot of aging bugs in there. According to the numbers, fully 50% of the bugs in the Future component are older than 1 month and more than 25% are older than 6 months. How this compares to other teams or areas, I can’t say, but it certainly makes me empathize with developers who feel their Future-ed bugs have gone walkabout.
If it makes you feel better in a sadistic way, the majority of bugs filed by RelEng team members go directly into the Future queue. We’re not overly happy about it either.
Things are getting done, though. For example, over the past month, the number of non-Future, release engineering bugs that are actively being worked on has gone from a low water mark of 130 up to over 200 today. For comparison, over the same period, the total number of bugs in the Future queue has slowly crept up from a low of 302 to 323. Mozilla is growing along so many axes that sometimes it feels like keeping the increase in the number of Future bugs to a linear relationship rather than exponential one is an accomplishment in itself.
So how do we stop the increase and start wrestling the Future component back under control?
The first step is triage. Starting this Thursday, February 11th, the RelEng team is going to have bi-weekly triage meetings to specifically prune down the Future queue.
As part of the triage, we’re going to be touching every bug and updating the whiteboard field with searchable tags. Our goal here is to make it easy to find classes of bugs in the Future queue so that duplicates and overlap can be easily eliminated, and fixes can be batched as much as possible.
We’ll be keeping a list of the tags we’re using in the wiki in case you want to follow along.
There are some classes of bugs that we won’t be able to eliminate (e.g. future goals), but hopefully within a few months, we’ll have the Future queue back under control.
It won’t be a quick fix, but it’s one we’re committed to.
I’m a bad conference organizer.
Why? Because we opened the An Event Apart 2010 schedule for sales back in, um, flippin’ November, and I never mentioned it here. Cripes, I never even posted when we announced the lineup of cities. I could go through the great big long sob-story list of reasons why 2009 was really tough and blah blah blah, but when you get right down to it, I fell down on my job.
Okay. So. Time to correct that.
(deep breath)
Hey everyone, check it out: the complete tour schedule for An Event Apart 2010! Woohoooo!
We’ve got a pretty killer lineup, if I do say so myself. You can get the mostly-complete list from our opening-of-sales announcement last November. It lists the people we had confirmed at the time; there have been a few additions since then. Check out your city of choice to see who’s going to be there! (But always remember that speaker lineups are subject to change: speakers are people too, and life has a way of interfering with schedules. I myself had to withdraw from An Event Apart Boston last year due to a family emergency.)
The price to register for these two-day, one-track Events is the same as it was in 2009, and there are educational and group discounts available for those who are interested.
But wait, I just said “two-day” when the first show of the year is clearly three days. What gives?
Seattle is the site of our first-ever A Day Apart, a full-day workshop that can be attended on its own or as part of a full three days of Event Apart ecstasy. And the inaugural Day Apart will be nothing less than a detailed plunge into HTML 5 and CSS3 with Jeremy Keith and Dan Cederholm. Jeremy handles the markup; Dan gets stylish. It’s going to be fantastic. I’m going to be in the back of the room for the whole day, soaking up as much as I can.
If you want to attend just the workshop, it’s $399 for the whole day if you buy an early bird ticket (available through March 5th). The price goes up $50 when early bird ends, and another $100 if you show up at the door. But I wouldn’t recommend that last, because I don’t think there will be any tickets available at the door. Again: if you show up unannounced on the day of the workshop and ask to buy a ticket, we will most likely have to turn you away, because I expect that there won’t be any seats available.
On the other hand, maybe you’d like to experience more than just one day of AEA goodness. Maybe you’d like to go whole hog and attend both the two-day Event Apart and the subsequent Day Apart, soaking up all the knowledge and enthusiasm and camaraderie that typifies An Event Apart. And who could blame you? If you do that, then the total early bird price for all three days is $1,190, whereas buying the event and workshop passes separately would total $1,294. That’s right: you actually get slightly more than $100 off the cost of the workshop if you attend all three days, over and above the early bird discount. (Or you can think of it as getting $100+ off the cost of the conference. We’re not fussy.)
As it happens, these three-day passes have proved quite popular. So if you want to get your hands on one of those—or on any Seattle tickets, whether one, two, or three days—I wouldn’t wait too long. Our internal analyses suggest that there will come a time, some time before the doors open on April 5th, that the ability to buy a ticket will cease to be. It may even pine for a fjord or two.
As for the four shows that come after Seattle, well, they’re looking pretty popular too.
I know I say this every year, but I’m really excited about what we’ve got planned for the year. Jeffrey and I constantly and (we hope) consistently strive to create an event that we ourselves want to attend, and that’s absolutely true of the shows and workshop we have planned in 2010. I can’t wait to hear what the speakers and attendees have to share. Hope to see you there!
Postbox now integrates with the Mac OS X technologies and applications you rely on most to get stuff done. Here’s what’s new:
Mac Address Book Support
Postbox provides read and write support for the Mac Address Book. Keep all of your contacts in one location and sync them with your iPhone or MobileMe service.
Send Meeting Invites with iCal
Apple’s iCal can now use Postbox for sending calendar notifications.
Search for Mail Using Spotlight
Postbox provides full support for Apple’s Spotlight to search through message bodies, message header information such as To: or From:, and attachment names.
Exchange Images with iPhoto
You can export photos directly from Postbox into iPhoto, and iPhoto will use Postbox to send photos as well!
Send Link from Safari
Easily send a web page link from Safari using Postbox. Very handy!
Lookup in Dictionary
Direct text-to-Dictionary lookups will help you quickly pick the perfect words.
Drag-to-Dock Message Creation
Dragging a file to the Postbox icon in the Dock will create a new message with the file attached.
Learn more about these new features and how to use them in our Quickstart Guide.
And now, with our new Refer-a-Friend Program, we’ve created an exciting way for you save on Postbox, or even get Postbox for FREE! See our Refer-a-Friend Program Page for details.
Our Refer-a-Friend Program is easy! Tell your friends about Postbox, and earn $5 each time someone purchases with your coupon code! Refer six friends and Postbox is effectively FREE!
Step 1 - Save $10 on Postbox!
Use your search skills. Find a coupon code to purchase Postbox for just $39.95 $29.95!
Step 2 - Share your Coupon Code
We’ll give you your own coupon code for “$10 Off Postbox.” Share it via Facebook, Twitter, your blog, email… anywhere.
Step 3 - Make $5 each time someone uses your code!
You get it - make 6 referrals and we’ll send you $30 - the price you paid for Postbox. Any more… and it’s all gravy.
There you have it. Postbox for about the price of a pizza, plus a way to earn it all back and give your friends a discount. Everyone wins!
To get started, search Google or Twitter for a coupon code to Save $10 on Postbox today! If you are an existing customer, simply select License… from the Help menu, and click Get Referral Code.To learn more, please see our Refer-a-Friend Program page, read our FAQ, or review the Terms and Conditions.
A special “Thanks!” to Charlie Wood of Spanning Sync for his help and advice on the development of this program.
Recently, I found that I needed my chrome Mochitest to wait for a XBL binding to apply, before continuing the test. For the end-user, waiting is hardly an issue - by the time they see the new user interface, all the bindings have applied. Mochitest (and most other automated test harnesses) runs straight through, and brakes for nobody. In some cases you can pull some trickery with nsIThreadManager, convincing Firefox to wait... but that's hardly reliable.
So I came up with a three-part solution.
This new test harness, which I call PendingEventsTest, adds a layer of complexity on top of SimpleTest. Each test function is added via PendingEventsTest.addTest(), and you can pause for a DOM event with PendingEventsTest.addEventLock(). The whole test sequence can abort with an error by calling PendingEventsTest.abortFail(). You can advance to the next test function in the sequence with PendingEventsTest.asyncRun() or PendingEventsTest.run().
There's more complexity to it than that, of course. To move data from one test function to another, I also added "payload" support, for storing a generic object. Also, this is written for chrome Mochitests - it will likely fail in content Mochitests. Still, this new test harness helped me finish support in Verbosio for my equivalent of the <xbl:children/> element in markup templates.
Lastly, it (and the logging service I wrote a few weeks ago) is licensed under MPL 1.1/GPL 2.0/LGPL 2.1, so anyone who wants to borrow this for Mozilla code is welcome to. Cheers!
On Friday night our family stayed with my parents on a boat up at Mahurangi, in Lagoon Bay. Easterlies had been blowing steadily for a few weeks and probably pushed a lot of plankton inshore, which helps explain what we saw that night.
About 10pm, after most of the crew had gone to bed and it was very dark, I noticed unusual flashes of light in the water. It was obviously bioluminescence caused by plankton, but far more intense than I've ever seen before. Even in still water, there were tiny points of light winking like flickering stars. Anywhere water was disturbed, it glowed brightly. Fish jumped, and the ripples formed bright, expanding halos. You could see moving, oscillating, sinuous lights underwater that I presume were fish swimming. I hopped in the dinghy with my wife and rowed around. The splashes of the oars created amazing flashes and patterns of light, and the dingy left a glowing wake. My wife dipped her hand in the water and it came out luminous.
It was an utterly remarkable experience --- like the bioluminescent forests of Avatar, but with the considerable advantage of being real. (Sorry, no photo --- the lights were only bright relative to the darkness of the night, and I lacked the technology and skill to capture them.)
One common thread running through the many different and interesting WebGL projects out there is that they all need to do vector and matrix math, do it quickly, and do it in JavaScript. To date, developers have either rolled their own, or they've used Sylvester, a fairly featureful vector and matrix JavaScript library.
One of the problems with Sylvester is that while it's fully featured (arbitrary NxN matrices and vectors can be created and manipulated), it suffers in performance because of it. Since this is such a crucial part of a successful WebGL program, I've put together a small package that I'm calling mjs.
mjs is designed around speed and simplicity. For example, it doesn't attempt to stuff vectors and matrices into JavaScript objects. Because the language offers no operator overloading, there's very little benefit in treating these types as discrete objects, and lots of performance and memory usage downsides. Instead, it provides a set of functions for performing operations on vectors and matrices, which can be any array-like object. For any function that returns a vector or matrix, an existing array can be passed in to take the result, or the function can create a new one. Array reuse ends up being important because of the potential for expensive garbage collection churn eating away at performance.
Here's a sample of the API:
var r = M4x4.rotate(Math.PI/2, V3.$(0, 1, 0), M4x4.I);
Note that V3.$ and M4x4.$ are shorthand for creating a new V3 or M4x4 (I wanted to use V3() and M4x4(), but that didn't work out too well since functions have a length property). However, because all they return are just new array-like objects, you could also write:
var r = M4x4.rotate(Math.PI/2, [0, 1, 0], M4x4.I);
If the WebGL types are available, those will be used for newly created vectors/matrices. They are a significant performance boost especially for repeated operations; but for specifying one-off vectors such as the above, literal array syntax is fine.
The rotate function internally makes a rotation matrix, and then multiplies it by the given matrix. So the above could also be written as:
var rotation = M4x4.makeRotate(Math.PI/2, [0, 1, 0]); var r = M4x4.mul(M4x4.I, rotation);
(The last line being redundant given that we're multiplying by the identity matrix.)
All methods that return a vector or matrix take an optional final argument, that of an existing object to reuse. For example:
var m0 = M4x4.$(); r = M4x4.mul(someMatrixA, someMatrixB, m0); // r == m0, so the assignment isn't necessary, but it's handy for chaining // .... do something with r ... r = M4x4.mul(someMatrixB, someMatrixC, m0); // r == m0 still // ... do something else with new results ...
Without allocating any additional temporary objects.
As mentioned before, one of the goals of mjs is performance. Matrix multiplication is one of the most common tasks, so here are some numbers comparing mjs, Sylvester, and native C code. This was run on a Core i7 desktop using a local build of Spidermonkey, which included one patch that's about to go into the tree that fixes the no-reuse tracing case. (Without it, the no-reuse tracing case is much larger because it's never actually jitted.) The test is simple: it multiplies two matrices together in a loop 1,000,000 times.
| Test | Time |
|---|---|
| mjs, JIT, matrix reuse | 140ms |
| mjs, JIT, no reuse | 533ms |
| Sylvester, JIT, no reuse | 5,280ms |
| mjs, no JIT, matrix reuse | 25,833ms |
| mjs, no JIT, no reuse | 26,681ms |
| Sylvester, no JIT, no reuse | 41,996ms |
| Native C++, SSE2, matrix reuse | 71ms |
| Native C++, SSE2, no reuse | 142ms |
(I also have numbers for MSVC without the SSE2 compile flag, but the numbers vary greatly depending on whether the values eventually go to infinity or not; if the values end up trending towards 0, the non-SSE2 code tends to win at around 52ms vs. 71ms; if the values trend to infinity, the non-SSE2 code takes around 11,000ms!)
Those numbers are pretty encouraging -- having native code be only 2x as slow for something like this is pretty nice to see. Granted, this is only a very isolated test, and I'm sure there are some tricks to optimizing the native code case (it's currently just a fully unrolled set of multiplies and adds). The "no JIT" case is less nice, but I'm sure that our Jaegermonkey folks will be all over this testcase (right, guys?). In any case, ideally most WebGL rendering loops will be fully traced in Firefox, so it would be less of an issue.
mjs is still very much a work in progress; it's missing a test suite and a whole bunch of features. You can find it hosted at Google Code, at webgl-mjs. (Side note: I couldn't just call the project mjs because a project called mjs was abandoned on Sourceforget 5 years ago, and Google Code complained.) There's also some documentation, viewable online here.
Bugs and contributions welcome!
Thanks to hard work by a whole bunch of folks, we shipped Lanikai Alpha 1 (the first development release of Thunderbird after 3.0) yesterday. More details about Lanikai can be found on the project page.
This release is a first in several notable ways:
* we're now requiring automated tests to land with most code changes
* the release cycle was much shorter than any development release in recent memory
* we're now having to do development and releases across both a development and a stability branch.
We've already learned a bunch of stuff from all the changes, and I expect that learning to continue for a little while before we're fully in a groove.
Thanks to everyone who has been part of making the release happen!
A common situation I run into is that I have some testcase, I profile it, then I optimize one of the things that looks slow a bit and reprofile. If I'm lucky, then the fraction of time it takes drops from B to A (A
Obviously, what it means depends on both A and B. If we assume that the time taken for the part that wasn't optimized hasn't changed, then the overall speedup is (1-A)/(1-B).
So B - A = 5% would mean a 2x speedup if B is 95% and A is 90%, and only a 1.05x speedup or so if B is 5% and A is 0%. If B is something like 53% and A something like 48%, then you get a 1.11x speedup.
All of which is to say that focusing on the hotspots is _really_ the way to go, if at all possible.