Flex/Flash/Actionscript

Analyzing the size of the Flex framework (or why I hate the AdvancedDataGrid)

In my recent Flasher Magazine interview I talked about how much I dislike the “advanced” classes in the Flex SDK that were shipped with Flex 3, namely the AdvancedDataGrid, the OLAPDataGrid, and the grouping and hierarchical collection classes. I also said that I thought that all the list-based controls (DataGrid, Tree, List, etc) were too bloated and slow and that they should all be rewritten from scratch. I realized that that sounds a bit harsh, so I wanted to try to back up those statements with some code metrics.

I’ve put together a spreadsheet that includes each class in the Flex framework, including charting and the advanced data visualization package. This shows the number of lines of code in each file, breaking down the total number of blank lines, comment lines, and actual code lines. I’ve colored the rows to indicate if the class belongs to the advanced data visualization package of Flex 3 (yellow), the charting framework (blue), the AIR SDK (red), or the open source Flex SDK (white).

Here are the top 20 classes, ordered by actual lines of code (not counting comments and whitespace):
screenshot086

To get these numbers, I used a free program called cloc to analyze the source code. Cloc is a perl script that analyzes a bunch of different languages, including ActionScript.

For the full list, check out the spreadsheet. This is for version 3.0.0 of the Flex SDK, it does not include anything released in SDK versions 3.0.2 or 3.2 or any of the new Flex 4 classes.

So just look at that list of top classes. Out of the top five, three of them are the new classes for the AdvancedDataGrid. It’s also worth nothing that AdvancedListBase and AdvancedDataGridBaseEx are not used for anything other than base classes for AdvancedDataGrid. If you look at the inheritance chain for AdvancedDataGrid, it looks like this:

UIComponent
ScrollControlBase
AdvancedListBase (4,553 lines of code, 8,573 total)
AdvancedDataGridBase (1,184 lines of code, 2,084 total)
AdvancedDataGridBaseEx (4,503 lines of code, 7,428 total)
AdvancedDataGrid (5,385 lines of code, 8,432 total)

That means that the entire codebase for the AdvancedDataGrid is 15,605 lines of code (26,517 if you include comments and whitespace). That’s 7% of the entire Flex codebase in those 4 classes. Note that this is not including ScrollControlBase or UIComponent, only the new classes in Flex 3. Also note that AdvancedDataGrid doesn’t inherit from ListBase or DataGrid at all, and ListBase is the second largest class in the entire framework.

So this means that when I run into a bug in the AdvancedDataGrid (which has happened a lot), I’ve got about 30,000 lines of code to wade through to try to debug my problem. No thank you.

The other two out of the top five are ListBase (which is why I said the entirety of the list classes is too big) and UIComponent (which I think is understandable, and I haven’t run into too many problems that have root causes in UIComponent, unlike ListBase which continues to be a big headache for me). Then number 6 on the list is DataGrid (oh, but don’t forget about #12 on the list, DataGridBase). If you group all list-based classes together (meaning the advanced classes and the original list/datagrid/tree classes), you’ve got 9 out of the top 20.

Code quality
This post is only about raw numbers. There’s an entirely different topic of code quality that I can write post after post about when it comes to the quality of the AdvancedDataGrid (and related classes). They use noticeably different coding conventions, they deviate dramatically from the best practices employed by the other components, and they are plagued by performance problems. But that discussion is for another post. For now I just wanted to point out the shear massive volume of code that you’re using when you use these classes.

Am I being too harsh?
Some would argue that the classes have to be big, given that they do so much. After all, it is called the AdvancedDataGrid, it’s doing crazy advanced stuff. I call bullshit on that argument. In my opinion, I just don’t think there’s an excuse for such massive classes. They make developers lives miserable when trying to debug, but I also think it is indicative of a sloppy coding style. The mentality sort of seems to be “throw more code at the problem until you get it to work.” Check out the expandItem method of AdvancedDataGrid. It’s 445 lines long – this single method is longer than 80% of all the other Flex classes in the framework (yes, I checked how many classes are under 445 total lines). That method even includes a spectacular commented out block of code with this comment:

// Dont know why this is done
// So, commenting it and using the rowHeight instead

Awesome. I guess as long as it passes the unit tests go ahead and ship it šŸ˜›

Standard
Flex/Flash/Actionscript

What my Eclipse/Flex Builder setup looks like

A few months ago I decided that my Eclipse setup was far from optimal. I was using slightly customized versions of the default Flex Development and Debugging perspectives that ship with Flex Builder. I had customized them to suit my personal preferences (things like making the Variables pane take up the full screen height). But the biggest problem I had was the debugging perspective. When you have all the panes you need open on the same screen (code editor, debug panel for stepping through lines, variables pane for inspecting variables, console for reading log statements, navigator for selecting different files) you end up with a tiny area for actually reading the code in the code editor.

The old single-screen perspective
Here’s a screenshot showing how bad my debugging perspective could become:

singlescreen_debugging

I’d usually try to edit code within a maximized code editing window by double clicking the code editor I was working in, then restoring it back to the small size when I was stepping through debugging. And often I’d hide the console view or move it around so I could get more vertical space. But in the end it was always a struggle to have access to all the pieces I needed and still be able to edit code.

The new dual-screen perspective
So I finally decided that having Eclipse within a single monitor just wasn’t going to cut it. For most of my development work, I plug my laptop into an external 22-inch monitor, which gives me a resolution of 1680×1050 on my external monitor and 1440×900 on my laptop monitor. When I was using Eclipse on a single screen I would always put it on the larger screen to maximize space. But now I decided to move all the panels other than the code editor and file navigator to my laptop screen instead (which sits just to the left of my external monitor).

My current setup looks like this (this image is small, but full res images of each screen follow):

side_by_side

My main external monitor screen is the one on the right and is dedicated to viewing and editing code. I’ve stripped everything else out, and even stripped down the default Eclipse toolbar items to only those that I actually use on a daily basis.

Right screen (external monitor):

dualscreen_right_annotated

Left screen (laptop):

dualscreen_left_annotated

Now I always have a code editor that takes up the maximum amount of space I have. I originally tried moving the File Navigator to the left screen as well, but found that a) it was a bit of a pain visually to have to move my eyes to the left and then to the right after selecting a file, and b) it’s the vertical space that counts the most in the code editor, not maximizing all possible horizontal space.

So when I debug I use the debugger and variable inspector on the left screen to step through line by line, while viewing the actual code on the right.

I’ve setup 4 main perspectives that include a Debug and a Development perspective for both a single-screen setup (when I unplug) and a dual-screen setup. I have all those shown at the same time in the perspective switcher toolbar, so I can easily jump back and forth between them. Also shown in this screenshot are the Team Synchronization and SVN Repo Exploring perspectives and single and dual screen versions of the Flex Profiling perspective. These 8 perspectives are pretty much the only ones I ever use, and are always a single click away.

screenshot085

Drawbacks
The most annoying issue I’ve run into has to do with the popped out Debug window and how Eclipse manages window focus. Usually when debugging it works great, I click the step-over or step-into buttons in the Debug panel and it works just like I want. But sometimes (and I can’t figure out why) Eclipse decides that when I step over a line of code (or maybe it’s only when hitting a breakpoint) that the main code window should get the focus, which means that it takes a click on the Debug panel just to bring it back into focus, then a second click to step over the next line. It doesn’t sound like a big deal, but when you’re used to a single click always making the Debugger do the next step, and then that turns into two clicks, it gets really annoying and frustrating.

The only other drawback is that Eclipse isn’t smart enough to know that I have one perspective for my dual monitor setup and one perspective for when I unplug my laptop from the external monitor. So the default behavior when I unplug is to end up with something horrendous like this:
singlescreen_messedup

That’s easy enough to fix though, by simply right clicking on the perspective icon the toolbar and selecting “Reset”:
screenshot079

It also took a little getting used to to be able to share my attention between both screens and quickly scan my eyes back and forth. Usually I’m used to keeping my laptop screen for certain tasks (email, chat, RSS reading, etc), so I have a bit of a mental block against using both monitors for the same task. But I’ve gotten pretty used to that by now.

What about you?
I’m curious what other Flex developers do in terms of laying out their IDE. I’d love to see screenshots of what other people have figured out. I haven’t experimented with too many different dual-monitor layouts, the one I’m using now was sort of the first one I made on the fly and have stuck with. But if you have a better system then I’d love to see it!

Standard
Flex/Flash/Actionscript

Flex and Guns on Flasher Magazine

Lee Brimleow just posted issue #2 of his sweet Flasher Magazine video mag. For this issue Lee interviewed me about Flex development, what I hate about the Flex SDK, what I think about Flash vs Flex. And then after the interview we went to shoot handguns at a shooting range in San Francisco šŸ™‚ Check it out, I hope you enjoy:

FlasherMag

This issue also includes interviews with Phillip Kerman and Robert Reinhardt.

Thanks to Lee for giving me the opportunity to do the interview, and for putting rounds of ammo on the Adobe corporate credit card!

Oh yeah, and here’s a quick still shot from the video’s intro sequence. I’m so proud:

Standard
Flex/Flash/Actionscript

Accessing SVN Repositories with ActionScript

I’ve been working on an ActionScript library that can load revision history from Subversion (SVN) repositories. This is something that I’ve had in the back of my mind for about a year now and finally sat down and figured out a way to do it. I remember seeing a post way back in September of 2006 on Ted Patrick’s blog talking about someone who had written a SVN library using the Socket class. As far as I could tell, this was the only mention of the project, and it was never released publicly. So I decided to figure out how I could read SVN revision history with AS3. I’m releasing the library in its current state (more on that in a second) as an open source project.

Quick demo and the code
Since I know people don’t like reading, I’ll post the code at the beginning of this post and show some screenshots and a demo AIR app that uses the library. If you want to tune out after this, it’s cool, I understand.
Download as3svnlib source code, or just the compiled swc file.

Demo
Since this uses socket communication on port 80, which is off limits under normal circumstances due to Flash player security restrictions, you have to run the demo as an AIR app. Lame, I know. You can install this tiny AIR app to try out the library if you want. The demo app will let you enter the URL of a repository and load the last few revisions. The repository must be publicly accessible for the demo to work (note that the library itself allows you to use basic authentication, but I didn’t build support for that into the simple demo).

The screenshot below shows the bare-bones example AIR app. You can enter a URL for a SVN repo and then you can load the latest revision number or you can load the last 50 revisions. That’s all you can do in the app, but with the library you can get more detailed information about all the revisions and you can decide exactly which revisions you want to load (or load all of them).
screenshot053
You can download the example AIR app if you want to see if it works with your SVN repo (again, note that this demo app won’t work with URLs behind authentication, but read below about how to do that). View-source is enabled on the AIR app itself once you install it, or you can view the source of the example here.

The scope of this library
My immediate goal was to load revision history, complete with commiter name, date, comment, and ideally more detailed information about which files were affected or scope of the changes. I was not looking to build a full SVN client capable of committing changes or doing diffs or anything fancy like that.

How I went about it
I first started thinking I would implement a legit SVN client that would connect to a server using a socket connection and use the SVN protocol to communicate. I read up on the protocol and it didn’t seem all that complex, especially if I was going to limit myself to read-only operations. However, when I first started down this road I realized I didn’t know shit about doing socket communication in ActionScript. So I downloaded as3httpclientlib (current source is at github here), which is an AS3 library for doing HTTP communication written by Gabriel Handford. My goal was to use that project to learn how to do my own socket stuff and then build my SVN library.

But once I got my head around the http client stuff I learned something even more important. Turns out that most SVN installations include an Apache server that lets you browse the repo with a web interface. What’s even more interesting is that Subversion uses the WebDAV protocol as well, which is a protocol based on HTTP for source control. Suddenly I had a new option that didn’t require writing my own full-on SVN client. Fuck yeah! Less work for me!

So I extended as3httpclientlib and added in some basic support for WebDav (namely the PROPFIND request and a basic REPORT request). Then I added in support for some custom reports that Subversion uses, namely log-report. All the reports that Subversion supports via WebDav are documented here. When you request a report you send a custom HTTP request to the server and fill the request body with some XML that defines what kind of report you want. Then the server sends back its response in XML.

Then I was able to use simple XML parsing to read my list of revisions, which included revision number, creator name, date, comment, and details about all the files that were added, removed, modified, etc. Easy breezy.

Most basic use of the library
To use the library you interact with the SVNClient class. This class is used to fire off all your requests (either to get the latest revision number or to get specific sets of revisions). All requests are asynchronous, so you need to add an event listener to the SVNClient class, then send off your request, and then handle the result.



	
		

Or here’s another very simple example that uses all MXML:




	

	
		
		
	

	
		
			
			
			
			

		
	


Accessing repositories with authentication
The library supports using basic HTTP authentication to access repositories as well. Essentially all you have to do is pass the username and password into the SVNClient constructor, so instead of just calling var client:SVNClient = new SVNClient(), you would call something like var client:SVNClient = new SVNClient("username", "password");. Note that just like with all browser HTTP basic authentication, the password is sent using a Base 64 hash that is easily decoded.

But for a more secure connection, thanks to the SSL stuff that’s included in the as3crypto library and used in the as3httpclientlib library, you can also access SVN repos using HTTPS. If there are repositories that use Digest (as opposed to Basic) HTTP authentication, I do not currently support that. Frankly, I don’t have any repos I use that use digest authentication, so I don’t have any way to test it (or desire to write it).

Going further
If I was going to build a full featured SVN client I would probably still try to do a custom socket approach that spoke the SVN protocol. The WebDav interface seems a bit limited compared to “real” Subversion commands, and I would be worried that it wouldn’t be good enough. However, WebDav does support stuff like updating files and committing changesets, so I think you could add in some basic committing functionality and still use the WebDav approach. I don’t have any immediate plans to do any of this, for now I’m happy with the capability of reading from a repository (I’ll write more later about an application I’m working on that uses this library). But if you’re interested in taking this code and adding in more support for things like checking out full revisions, committing changes, etc., please be my guest.

License
Since this uses the as3crypto library, which is licensed under the New BSD license, I’m not entirely sure what that means for my code. I’d like to say mine’s MIT, but if I have to say it’s New BSD (which is almost just as flexible), then I guess I’ll say it’s New BSD. I think that really just means that I need to include the license file that contains copyright information in it when I redistribute the as3crypto library (which I have done). So you can pretty much do whatever you want.

Standard
Flex/Flash/Actionscript

Get me on the 360|Flex speaker list!

[UPDATE: apologies if this showed up as new in your feed readers when it isn’t, I had a database problem and had to restore two old posts. Also, the voting has now been closed, so no need to go and vote, thanks to everyone who voted!]

John Wilker just posted all the speaker session submissions that they received for 360|Flex and he’s letting the community weigh in on what they want to see at the conference. The sessions don’t list the speaker names, although with a little reading I could figure out some of them (my money’s on Labriola for the “Kicking Ass and Taking Names” session. [update] I was wrong on that one, looks like Joseph Balderson submitted the kicking ass session). My session’s title is Cool Shit: Inspiring Creation and Creating Inspiration. The fact that I drop the s-bomb in the title and my description includes the phrase “holy shit, that’s fucking amazing” might give away the fact that it’s mine šŸ™‚

Here’s the description I submitted, which should sum up the kind of presentation I want to give:

By the end of 2008 I had burned out. Flex development had become a job – a real job, a normal job – and I wasn’t experimenting and playing with the technology like I used to. So I decided to go on a quest of rediscovery. I was determined to find the magic again, that spark of “holy shit, that’s fucking amazing!” that comes when you’re so inspired by someone’s work that you stay up until 4 in the morning trying to create something as cool.

This session will include examples of Flex and Flash projects and experiments that have re-inspired me. I’ll talk about why I fell in dorky love with each example, and then dive into what that inspiration led me to create. Inspiration is a cycle, and I hope that by sharing my own inspiration and my own creations I can provoke others to do the same. We’re all in this together, and there’s so much cool shit to explore.

This is sort of a self-therapy session for me. Over the next few months I’m going to be focusing my effort on playing again, like I used to when this technology was new to me. I want to bring back that intoxication with the technology that I first had when I started learning Flex.

So if you think the session idea sounds good, go and vote for it! Make sure to vote for all the other ones you want to see too, the list of sessions is really long (126!) so it takes some time to read through them all.

Standard
Flex/Flash/Actionscript

Is that Flex on my Kindle?

Well, not really… but it’s a Flex book šŸ™‚

flex_kindle1

While I was getting ready to travel for the holidays I was buying a few new books for my Amazon Kindle to read on the plane. As I was browsing through the online store right on the Kindle, there in my recommended books list was Creating Visual Experiences for Flex 3 by my friends Juan Sanchez and Andy McIntosh. Out of sheer curiosity I was forced to instantly buy it, wondering what it would look like on the Kindle’s screen.

Note that this isn’t in any way a review of the actual content of the book, since I haven’t read it yet. But knowing Juan and Andy I’m sure it’s fantastic. I just skimmed a few chapters trying to see what it looked like on the Kindle’s screen.

Text and Images
Turns out that reading the textual content of the book on the Kindle works great. The images leave a little to be desired, since they’re rendered (like all images in a Kindle book) in fairly minimal grayscale, but they don’t actually differ that much from the print book (also in black and white) and you usually don’t lose any important information by viewing the images on the Kindle’s screen. Some of the screenshots comparing different effects and blend modes didn’t work very well since they were so small and the low contrast makes it difficult to notice differences.

Tables
Tables actually turned out pretty readable, although quite small. But I was impressed how well the tables were actually preserved, and assuming you don’t have a problem reading small text (which I didn’t) then they’ll work just fine. If you’re old and your eyes are feeble then this might be an issue.

flex_kindle_table

Code Samples
The code listings are a bit more problematic. With the normal font size, the code listings become pretty unreadable on the Kindle’s screen. Pretty much all the code wraps in weird ways, breaking the lines up, often mid-word, and usually spilling over onto multiple pages.

flex_kindle_code

However, if you adjust the font to the smallest that the Kindle offers, then you get more readable code listings. Things still spill over across pages, and sometimes the lines wrap awkwardly, but overall the code listings are much improved. The smallest font size is really the only way to read a book like this. Truthfully, I imagined the code listings would be completely unreadable, but if you adjust the font size it’s much better than I ever imagined it would be.

The difficulty with code listings makes the Exercises section (section 4) difficult to get through. But the previous sections, which give you explanations of the skinning and styling techniques and discussion about all the particular components within the Flex framework, rely on much shorter snippets of code sprinkled in the text. The exercises are really code-heavy (as they should be), which makes viewing on the screen hard.

Of course, reading code on such a small screen (regardless of whether you’re reading a book or reviewing someone’s code or whatever) is far from ideal. I’d never choose to write code on a screen this size, and reading it here is certainly less than perfect. But reading code in any print book is always relatively awkward, with the only real difference between print and the Kindle being that print books have better formatted line breaks and the ability to see multiple pages at once (assuming the two print pages can be open side by side).

Overall, if you’re comfortable reading the entire text at the smallest font size, it’s pretty decent actually (again, I’m referring to the viewing experience, not the content of the text). I don’t think I’ll get any other programming books on my Kindle, instead I’ll buy the print versions if I have the choice (or more likely I won’t buy programming books at all, as I’ve written about previously). But if you’re traveling and you don’t mind the layout issues, there’s no reason you can’t learn Flex styling and skinning on an airplane.

P.S. For worry of breaking some unknown clause in my contract with my own publisher, I better tell you that I wrote a Flex book too! Deepa Subramaniam and I wrote Adobe Flex 3 for Dummies, which is awesome (although it’s not offered on the Kindle). Juan and Andy’s book and our Dummies book really target very different audiences, so if you’re just starting to learn Flex then you might want to check out our book first and then move on to Creating Visual Experiences.

P.P.S. Merry Christmas and happy holidays!

Legal stuff to try to keep me from getting in trouble
All images in this post are digital pictures I took of the Amazon Kindle displaying the Creating Visual Experiences with Flex 3.0 book, written by Juan Sanchez and Andy McIntosh and published by Addison-Wesley. All content is copyright Pearson Education, Inc. The images used in this blog post reproduce very small amounts of text and images from the original text, at very low quality in comparison to the original. The intent of this post is to explain the reading experience on the Kindle, not in any way to redistribute copyrighted content. I will, without argument, remove any images at the authors’ or publisher’s request.

Standard
Flex/Flash/Actionscript

Slides from my Flash on the Beach session on decompiling SWFs

Here are the slides from my presentation that I gave today at Flash on the Beach. The presentation covers decompiling Flash and Flex SWFs and includes an overview of the tools available, a few examples of the kind of code you might see, and some security suggestions. I will not be posting any of the code that I showed during the session (apart from the very tiny snippets in the slides). I think it’s pretty obvious why I’m not going to post the decompiled Photoshop Express code šŸ™‚

I don’t think there’s any formal feedback survey or anything at FOTB, so if you were at my session I’d love to hear what you thought about it. You can email me at doug@dougmccune.com or leave some comments here. Let me know what you liked and what you didn’t.

Standard
Flex/Flash/Actionscript

If you steal source code, don’t ask for help fixing it

While doing some research for my decompiling session at Flash on the Beach, I came across this gem of a post on the Adobe ActionScript 3 message board. Someone posts a block of code and asks “Iā€™m getting 3 compiling errors when I test my flash movie: could you guys give me some advice on how to sort out these issues and correct them. its driving me crazy trying to resolve the problem.”

And then he posts the code. And if you have ever decompiled any ActionScript code, it’s painfully obvious what the guy is doing: he’s ripping off someone else’s code, then complaining in the Adobe forum that he can’t figure out why it won’t compile, and asking people to fix his broken, stolen code.

Here’s a snippet of his code:


public function BEShell()
        {
1  0 39            instance = this;
            Logger.target = new FirebugTarget();
            var _loc_1:* = loaderInfo.loaderURL;
            if (_loc_1.indexOf("env1") != -1 || _loc_1.indexOf("Akqa") != -1 
                        || _loc_1.indexOf("dev.site.com") != -1)
            {
            }
            else
            {
                Logger.mode = Logger.PRODUCTION_MODE;
                stage.addEventListener(KeyboardEvent.KEY_UP, keyHandler);
            }// end else if
            return;
        }// end function

That’s very clearly, without question, decompiled code. It even has some extra line number information included in the dump! And that’s what was tripping the guy up. He couldn’t understand why that beginning line that starts with “1 0 39…” wouldn’t compile!

Sometimes I’m just amazed by people. Like, really? You have the balls to steal someone’s code, then post it in a public forum and ask for help?

And of course maybe I’m totally off base, maybe the guy works for the company that originally wrote the code (seems to be a Flash agency called AKQA) and maybe he just got pulled in to fix some co-workers work and they lost the original source and they need to use decompiled code since that’s all they have… yeah… maybe…

Standard
Flex/Flash/Actionscript

I just decompiled a decompiler so I could use it to decompile itself

Update: Turns out that the code in Nemo 440 is actually just the code from the abcdump.as file in the Tamarin project. It looks like the abcdump.as file was written by Dan Schaffer from Adobe. So it turns out I could have just grabbed that file and not decompiled Nemo 440 at all, oh well šŸ™‚ Shigeru Nakagakai has also used that same abcdump.as file to create his own AIR app that lets you compare SWFs and inspect classes and packages.

My brain almost exploded with meta-geekiness. If you haven’t seen the Nemo 440 AIR app, it’s a SWF decompiler written in AS3 as an AIR application, written by Vadim Melnik. It lets you load SWF files (or SWCs) and it will show you a list of all classes in the SWF, as well as the detailed ABC bytecode for each class. Technically I guess using the word “decompiler” isn’t correct, Nemo 440 is a SWF disassembler that produces ActionScript Byte Code (ABC). This isn’t the same as a true decompiler that produces real ActionScript code (like the Sothink Decompiler).

So if you download and play with Nemo 440 you’ll see what it can do. Basically you can see all the classes in any SWF, and all the methods within those classes. You also get to see some stuff like class-level and static variables. Then if you want to uber geek out you can see the ActionScript Byte Code of the SWF. That means you get shit that looks like this:


    0       getlocal0     	
    1       pushscope     	
    2       getlex        	http://www.adobe.com/2006/flex/mx/internal::layoutObject
    5       getlocal1     	
    6       setproperty   	direction
    9       findpropstrict	invalidateSize

That’s far from being nice beautiful AS3 code that you can actually use, but if you spend enough time understanding ABC code you can start to make some sense of it. But even just seeing the packages, classes used, and the methods of all the classes is pretty awesome.

So after playing with Nemo 440 a bit I encountered the glaringly obvious question. What happens if I use Nemo 440 to decompile the Nemo 440 application itself? Excited in my geekery, I quickly extracted the SWF file from the AIR app and loaded it in, only to be sorely disappointed. When I decompiled the app I could see all the Flex classes and other libraries that were used (even some components from Flexlib!), but I couldn’t see any classes that were used to do the decompiling. Hmm, I thought, how odd.

I figured that it wasn’t technically possible that the dissassembler would work so well on all SWFs except itself, something was fishy. I mean, that just doesn’t make sense. So I decided to load the SWF into the Sothink Decompiler to have a look. Then I came across this little gem within the Nemo 440 source code:


private function _checkName(param1:String) : Boolean
{
   if (param1 != null)
   {
      if (param1.indexOf("docsultant") >= 0)
      {
         return false;
      }
      if (param1.indexOf("nemo440") >= 0)
      {
         return false;
      }
   }
   return true;
}

That code specifically checks if the package name matches one of the packages used in the Nemo 440 source code and excludes it from being processed! Mother fucker!

So I decompiled the code using the Sothink Decompiler, and then decided I wanted to put it back together into a running app. It took me about 6 hours or so of work, and I had to consult the SWF specification document and the AVM 2 spec document a lot during the process, but I got it working.

So then I had my own AIR app that used the code from the Nemo 440 app to load SWFs and disassemble them. The first thing I did, obviously, was load up the Nemo 440 SWF file and give it a whirl, and I was instantly looking at the full class/package structure and the disassembled ABC bytecode of all the classes.

Ahh, sometimes it feels so good to geek out so much.

For those interested in learning more about decompiling, disassembling, ABC bytecode, and all that good stuff, I’ll be talking about this whole thing and a bunch more stuff in my presentation at Flash on the Beach in Brighton, England on October 1st. I won’t be posting the code that I decompiled and put back together, unless I get the original author’s permission (which I’ll be asking for, but haven’t yet done). Who knows, maybe the guy will be cool with open sourcing it šŸ™‚ but maybe not. And if not, that’s cool too, he put a lot of work into it (I have a great appreciation for the amount of work after reading through much of the SWF spec and seeing the kind of code he had to write).

I just thought the concept of decompiling the decompiler to decompile the decompiler was too cool. God, I’m such a geek.

Standard
Flex/Flash/Actionscript

Followup for Using BitmapData for Array manipulation: using a hashmap is (a little) faster

UPDATE: The test app has been updated to include a third test that uses a ByteArray approach. Looks like the ByteArray approach is the fastest, followed by the hash table, followed by the bitmap method. They’re all pretty close when you’re working with 10k or 100k records, but once you get into a million or more items then the ByteArray approach pulls ahead. Thanks to Alex Bustin for sharing his code for the ByteArray test.

After I posted my technique for using the Flash bitmap drawing methods to perform calculations on arrays, Tom Carden started posting a few test of his own that tried to optimize some code-only algorithms. In his test he got an algorithm that used a hash table lookup method to be almost as fast as the bitmap method (but in his tests the hash table method was still slower than using bitmaps). I’ve created a slightly modified version of a hashmap algorithm that squeaks out just ahead of the bitmap test.

The algorithm basically just uses a very simple Array that holds boolean values that represent whether or not a particular item exists in the filtered array. So this is just like using the bitmap approach, except instead of creating different colored pixels, you just set the proper index in the array to true or false. Then once you have those two array of true/false values for both your filtered arrays, it’s just a matter of looping over the full array and checking the hash table arrays to see if a particular item exists in one, both, or neither of the filtered arrays.

And it turns out this is faster (but not by that much) than the bitmap method. But if you’re looking for the fastest way to take two arrays and find the unique values in either or the intersection or union, using this hash table method is the fastest way I’ve found so far. Too bad the bitmap stuff didn’t win, I was rooting for it… oh well, so it goes.

I’ve updated the test application (source) to include this new algorithm too, and here are the performance test results on my machine These stats were generated by taking the average of about 10 runs of each algorithm, running in the standalone Flash Player (which seems significantly faster than in any browser):

# of items Hashmap test Bitmap test
10 items 3 ms 4 ms
100 items 4 ms 4 ms
1,000 items 5 ms 6 ms
10,000 items 26 ms 26 ms
100,000 items 225 ms 237 ms
1 million items 2340 ms 2418 ms
2 million items 4874 ms 5705 ms
5 million items 13389 ms 14220 ms

And here’s the full class that I created for testing this has table algorithm:


package
{
import flash.utils.Dictionary;

public class ArrayHashProcessor
{
private var fullArray:Array;
public function setFullArray(value:Array):void {
	fullArray = value;
	reset();
}

public function reset():void {
	hashes = new Dictionary(true);
}

private var hashes:Dictionary;

public function filter(filterFunction:Function):Array {
	var newHash:Array = [];
	
	var filtered:Array = fullArray.filter( filterWithHash(filterFunction, newHash) );
	hashes[filtered] = newHash;
	
	return filtered;
}

private function filterWithHash(filterFunction:Function, hash:Object):Function
{
	return function(item:Object, index:int, array:Array):Boolean {
		var b:Boolean = filterFunction(item, index, array);
		hash[index] = b;
		return b;
	};
}

public function process(array1:Array, array2:Array):Array {

    var unique1:Array = [];
    var unique2:Array = [];
    var intersection:Array = [];
    var union:Array;

	var hash1:Array = hashes[array1];
	var hash2:Array = hashes[array2];
	
    fullArray.forEach(function(item:Object, i:int, a:Array):void {
        if (hash1[i]) {
            if (hash2[i]) {
                intersection.push(item);
            }
            else {
                unique1.push(item);
            }
        }
        else if (hash2[i]) {
            unique2.push(item);
        }
    });
                
    union = unique1.concat(unique2).concat(intersection);
    return [unique1, unique2, intersection, union];
}        

}
}

There’s nothing real complicated here (and certainly nothing as visually interesting as using bitmaps). Basically you need to take advantage of using the filtering of the array as the place where you store the true/false value in the hash table (using the bitmap method this was where we called setPixel() as well). Doing that extra step in the filter function doesn’t add very much time to the filter function (but sticking a boolean into an Array is faster than calling setPixel on a bitmap). Then when you want to compare the arrays we just loop over each item in the full array and check the two hash tables.

So I’m a little sad to see my bitmap method gets surpassed by something so simple, but hey, that’s just how it works out sometimes. I suppose I should’ve tried this method first šŸ™‚ but then I wouldn’t have gotten to play with bitmaps.

If you know of an even faster way to accomplish the same thing, let me know in the comments. I’m thinking about trying out using a ByteArray as an alternative to storing the hash lookups in a normal Array, but my gut tells me that using writeByte and readByte will be slower than simply setting array[index] = true, but who knows.

Overall I’m happy I tried out the bitmap approach (even if I won’t be using it). I think it’s a pretty interesting way to approach the problem and it helps illustrate that sometimes thinking outside the box can have some pretty cool results.

Standard