A Little Less Conversation, A Little More ActionScript
This is a modal window.
Das Video konnte nicht geladen werden, da entweder ein Server- oder Netzwerkfehler auftrat oder das Format nicht unterstützt wird.
Formale Metadaten
Titel |
| |
Serientitel | ||
Teil | 20 | |
Anzahl der Teile | 20 | |
Autor | ||
Lizenz | CC-Namensnennung 4.0 International: Sie dürfen das Werk bzw. den Inhalt zu jedem legalen Zweck nutzen, verändern und in unveränderter oder veränderter Form vervielfältigen, verbreiten und öffentlich zugänglich machen, sofern Sie den Namen des Autors/Rechteinhabers in der von ihm festgelegten Weise nennen. | |
Identifikatoren | 10.5446/32386 (DOI) | |
Herausgeber | ||
Erscheinungsjahr | ||
Sprache | ||
Produktionsort | Brüssel |
Inhaltliche Metadaten
Fachgebiet | ||
Genre | ||
Abstract |
| |
Schlagwörter |
3
4
7
8
17
18
00:00
ComputersicherheitFokalpunktHydrostatikAnalysisClientKernel <Informatik>AdditionPunktReverse EngineeringEin-AusgabeWellenpaketMultiplikationsoperatorSoftwareschwachstelleMereologieTwitter <Softwareplattform>Wurzel <Mathematik>Physikalischer EffektBildschirmfensterMomentenproblemResultanteBinärcodeProgrammfehlerKrümmungsmaßPerspektiveOffene MengeComputeranimationJSON
01:58
Lokales MinimumRechenwerkPunktRuhmasseDifferenteJust-in-Time-CompilerTypentheorieSoftwareschwachstelleFormale SpracheDemoszene <Programmierung>Vorlesung/Konferenz
02:26
SchnittmengeSoftwareschwachstelleKategorie <Mathematik>DebuggingGarbentheorieZeichenketteMaschinenspracheSystemaufrufProgrammfehlerBeweistheorieMereologieLineares FunktionalObjekt <Kategorie>TypentheorieMatrizenrechnungFormale SpracheFaltungsoperatorElement <Gruppentheorie>GeradeVarianzVerkehrsinformationBitFehlermeldungStatistische HypotheseSoftwaretestStochastische MatrixBinärcodeMultiplikationsoperatorHalbleiterspeicherElektronische PublikationStandardabweichungAnalysisCASE <Informatik>CodeSystemzusammenbruchSechseckSchreib-Lese-KopfSpeicherverwaltungWeb-SeiteMultiplikationZahlenbereichKlasse <Mathematik>Einfache GenauigkeitRechter WinkelSampler <Musikinstrument>Arithmetische FolgeGanze ZahlParametersystemKonstruktor <Informatik>Syntaktische AnalyseDämpfungAdditionMini-DiscE-MailMailing-ListeMaskierung <Informatik>Demoszene <Programmierung>WirbelströmungDatenflussPerspektiveKontextbezogenes SystemWeg <Topologie>BeamerDatenfeldVersionsverwaltungURLBruchrechnungServiceorientierte ArchitekturKonstanteWort <Informatik>Notepad-ComputerFreewareLesen <Datenverarbeitung>Filter <Stochastik>Richtung
11:10
SkriptspracheMaschinenspracheBootenFunktionalLineares FunktionalDatenstrukturAutomatische IndexierungSystemaufrufTabellePaarvergleichSechseckParametersystemAnalysisSchnittmengeProgrammfehlerCodeEin-AusgabeFaltungsoperatorCASE <Informatik>Bitmap-GraphikPrototypingZahlenbereichKategorie <Mathematik>MatrizenrechnungZeichenketteMailing-ListeWechselsprungVersionsverwaltungPatch <Software>Quick-SortNormalvektorBinärdatenDigitale VideotechnikDifferenteMultiplikationsoperatorKonstruktor <Informatik>MerkmalstrukturSpeicherabzugObjekt <Kategorie>MereologieParserImplementierungZweiCachingBefehl <Informatik>IterationMatchingDateiformatBinärcodeGarbentheorieInformationOpen SourceByte-CodeBitNabel <Mathematik>Klasse <Mathematik>LastRichtungMAPDämpfungDelisches ProblemTypentheorieOrdnung <Mathematik>QuellcodeNamensraumMetadatenInstantiierungKonstanteBildgebendes VerfahrenMultiplikationSchreib-Lese-KopfWort <Informatik>GradientEreignishorizontVirtualisierungAuswahlverfahrenTopologieTouchscreenMinkowski-MetrikGruppenoperation
19:53
Byte-CodeParserAusnahmebehandlungCodeMatrizenrechnungMakrobefehlFaltungsoperatorSystemaufrufInstantiierungInformationSyntaktische AnalyseZeiger <Informatik>DatenstrukturProdukt <Mathematik>BitSpeicherabzugZahlenbereichSechseckSchnittmengePatch <Software>AdressraumWeb-SeiteLineares FunktionalTypentheorieWort <Informatik>HeuristikMinimumFahne <Mathematik>DatensichtgerätObjekt <Kategorie>Funktion <Mathematik>Klasse <Mathematik>Algebraisch abgeschlossener KörperRechenwerkMatchingWeg <Topologie>VererbungshierarchieProgrammfehlerTabelleParametersystemFunktionalDebuggingMehrrechnersystemMaschinenspracheArray <Informatik>Kategorie <Mathematik>Konstruktor <Informatik>StellenringRechter Winkelp-BlockSampler <Musikinstrument>Web SiteGruppenoperationSelbst organisierendes SystemElement <Gruppentheorie>Metropolitan area networkTrennschärfe <Statistik>EnergiedichteMittelwertQuellcodeKonfiguration <Informatik>Algorithmische ProgrammierspracheRechenschieberCybersexInzidenzalgebraTopologie
28:37
MereologieKernel <Informatik>AnalysisSymboltabelleTypentheorieQuick-SortCodeSoftwareschwachstelleTypprüfungDämpfungCoxeter-GruppeSoundverarbeitungInformationGenerator <Informatik>BeamerDichte <Physik>TaskStrömungsrichtungDigitale VideotechnikAggregatzustandBinärdatenProgrammfehlerFuzzy-Logik
30:34
ZahlenbereichTypentheorieCodeInstantiierungAlgorithmische ProgrammierspracheKlasse <Mathematik>Algebraisch abgeschlossener KörperByte-CodeFunktionalMaschinenschreibenInformationNabel <Mathematik>AnalysisRechteckLeistung <Physik>Rechter WinkelGruppenoperationBildschirmmaskeAtomarität <Informatik>VersionsverwaltungCASE <Informatik>Lineares FunktionalWurm <Informatik>Computeranimation
32:31
HeuristikAlgorithmische ProgrammierspracheMereologieCodeInstantiierungRechter WinkelSystemaufruf
Transkript: Englisch(automatisch erzeugt)
00:09
on Brussels 2017.
00:21
All right, so I am Wandering Glitch. Jazel Spellman, I usually try and go by Wandering Glitch, as I said, I guess two talks ago. Focus on static analysis of binaries, most specifically on client signed vulnerabilities, both user land and kernel. As far as kernel land goes, I've typically spent most of my time in the Windows kernel,
00:42
but this week took Safan Esser's Mac OS and iOS training. So hopefully spending more time in OS X and that land as well. I also very much like to write automation to augment my reverse engineering efforts. And part of the reason for this is I'm part of Trend Micro Zero Day Initiative. We buy vulnerabilities, and I'm one
01:02
of the people that has to vet them, has to do root cause analysis on them to determine whether they're exploitable, whether they're interesting, harmful, impactful, so on and so forth. Our team is one of the top suppliers, because we're buying the vulnerabilities of vulnerabilities and CVEs for Microsoft and Adobe.
01:20
And that last point is actually probably the most important for this talk in that I, as a result, have to do a lot of analysis of Adobe vulnerabilities. As you can probably tell from the XSLT talk, we do a lot of reader bugs, but there's also a lot of flash vulnerabilities. And so I'm going to try and focus this talk kind of from my perspective, the analyst perspective.
01:42
In addition to doing security stuff, I have recently discovered that I very much enjoy travel. It's only January of 2017. I've been on four continents. I actually took my first steps on Antarctica in January 1st, which was quite awesome. All right, so opening up with a very, very minimal primer
02:02
on AS2 and AS3, and very, very minimal. Main thing I want to go is that, main thing I want to point out is that there are some massive API differences and behind-the-scenes JIT differences, but the only thing I'm really trying to point out is type enforcement, specifically because most of the vulnerabilities that
02:20
have been present in ActionScript 2 have been due to lack of type enforcement at the language layer. So here is an example that I lifted from Wikipedia, and hopefully that's readable. Most important line that I'm trying to call out here is var textHello, where, as you can tell, there's no real way to know what kind of object
02:40
that is just by knowing that you have a variable called textHello. Looking at the rest of it, you can kind of glean that it's probably a text field, because this function createTextField is being called on it. And then later on, in the next line, where you have .text being set to a string, you can kind of guess that that text property is expected to be a string, but there's nothing there
03:02
to enforce that for you. Additionally, if that assignment were to reach down into a C function, into native code, with ActionScript 2, there's nothing to force the object that you're setting it to be a string until you hit native code. What I specifically mean by that is if you were to do var textHello.text equals
03:21
textHello, then it would try and do type coercion on textHello, convert it to a string, and that would all happen within native code, not within the language itself. And that alone is part of why redefinition attacks have been so prevalent there. Here's ActionScript 3, also lifted from Wikipedia from the same page, actually.
03:42
And note that this time when you have var textHello, you have colon textField. So in this case, the language is enforcing the type of textHello to be a textField object. And if new textField returned anything that was not a textField or a descendant of, then it would throw an error and nothing else would continue on.
04:01
Likewise, with .text, it's expected to be a string, and assignment of anything that is not a string or can be coerced to a string will cause an error. And then, as I had said before, the API is quite a bit more massive than with ActionScript 2, and it's continuing to grow, whereas ActionScript 2 is basically stagnant.
04:22
I did see some modifications and some additions, but they seem to be rather silent, and nothing changed as far as the official API goes. So as I said, I'm gonna try and approach this from my perspective, the analyst's perspective. If you look at this crash, it is pretty worthless, especially since I accidentally clipped out the value of EDI,
04:43
which is register being read from. But I assure you, even with that, it's still pretty worthless. All you can really tell is that, if you run a bang heap on it or just try and read that memory, is that EDI, in this particular case, I have page heap on, and this value, it's freed,
05:01
and you don't really have any idea why. You can see the crash in the binary, but there's really nothing useful you can glean from it. If you try and run this on multiple versions, because Adobe Flash does get patched every month, you'll see roughly the exact same crash, but in varying locations. So if you were trying to do analysis on,
05:24
say, one case, that may not be too bad, but if you're getting 20, 30 cases over a course of a couple of months, that's gonna be a pain. There's no real easy way of being able to know for sure that two bugs are not duplicates of each other, or if they're maybe just variants where someone copied and pasted the exact same code and they just happen to be near each other.
05:43
So the crash itself is not that useful. We can look at the proof of concept. And the proof of concept, this is one I picked out, particularly because it was reported to us as part of Pwn2Own, but most interesting thing about this is the exact same vulnerability was present in both ActionScript 2 and ActionScript 3.
06:00
And the reporter for ActionScript 2 was Natalie Sivanovic, as well as an anonymous ZDI researcher. And then the ActionScript 3 vulnerability was submitted to us by Nicholas Jolley during Pwn2Own 2015. Looking at the proof of concept, and bit atypical, because I already knew what the bug was when I looked at this, but if we look at the proof of concept,
06:22
one of the first things that stands out is that you have a convolution filter, and then you have this new object with a custom value of property. And that function modifies matrix X in the convolution filter, and then in the very, very last line, it is used as part of an array, and all the other elements in that array is an integer.
06:43
And if you look at the value of function, it's also returning an integer. So we can kind of glean that there's probably use after free, and we know that because of it reading from free data, but also because a value is being modified, you have an array that is going to be iterated through.
07:01
That's the property being assigned to matrix. And you have what appears to be some attempt of reclaiming that freed memory by allocating new file reference objects. So this ends up kind of being a kind of your standard redefinition, re-entrant type vulnerability. As far as actually proving this, because right now we just have come up with a hypothesis.
07:22
There are ways of testing this dynamically, but we want to actually prove it by looking at the binary. To do that, we need to find and isolate where it is in the binary. Couple of needles we can look for. There's convolution filter, there's matrix X, and there's matrix. I, for whatever reason, chose convolution filter.
07:42
Matrix X probably would have made more sense, but doing a string search of this in, I think, flash debugger projector, but the same would apply for flash.ocx. We end up with a number of hits, and some of these are more useful than others. Some of these are not so interesting. I found convolution filter class and convolution filter object
08:01
to be a little bit more interesting, but those were not as helpful. If you go to the first one, you'll see that you're in a R data section, and for at least 1,000, 2,000 bytes in either direction, you just have other strings. Nothing really obviously interesting, but what I ended up doing is
08:20
I just wrote some quick IDA Python to start off at hex DB5318, and just keep iterating one head at a time over and over again until you hit a head that has data references to it. Actually had to do this a couple of times because there were some places where IDA thought that there was a reference, and it either was there by mistake
08:40
or not quite sure, but not quite what I wanted. So continuing on until we found something interesting, there is this FWS. For those who don't know, FWS is the magic bytes for an unencrypted SWF file. On a completely unrelated tangent, every time I've tried my hands in the bathrooms, it says CWS, I immediately think of compressed SWFs.
09:05
So if we look at these single data reference to FWS, we see that it is pushed on the stack, and right adjacent to that is an integer, hex 9C89, that is also pushed to the stack. Based solely on this, I kind of surmised that there's a SWF that's embedded inside Adobe Flash,
09:23
and it's present in Flash.ocx, and it's present in the Flash debugger projectors. So I ran IDA API.getManyBytes on hex DB3628 with a size of hex 9C89, and then dropped it to disk, and then just threw it into one of the freely availability compilers.
09:41
I used ffdec or JPEGs, and that resulted in a nice, clean ActionScript. It was ActionScript 2, and I did initially say I was looking for an ActionScript 3 vulnerability, but still, this is good progress. So we have a bunch of ActionScript 2, and everything seems to start off
10:01
by making calls to ASNative and AS Constructor, and all the calls to AS Native and AS Constructor consist of calls where you have two integer arguments and nothing more, and they all kind of seem to be constrained to values, and the first argument to AS Native and AS Constructor seems to be used a lot.
10:21
As you can see here, an escape, an escape, parse in, and parse float all have 100. In addition to that, there's a lot of calls to AS Set Native and AS Set Native Accessor, which are based on calls from AS Native, and the interesting thing is there's a lot of strings that are used
10:40
in AS Set Native, AS Set Native Accessor, so that's clearly where accessors and properties are being put onto arbitrary objects, but AS Native and AS Constructor are not actually set anywhere. Clearly, they must be defined and created somewhere else, so I went back to the binary, and I did a search for AS Native and found two hits.
11:01
First hit was within the SWF, I just dumped a disk, so not interesting, but at least confirmation that it's there. The second one was in the R data section and actually had a data reference to it and kind of should have done, I apologize in advance, I kind of should have taken my screenshots before actually running my script
11:21
because I ruined it. As you can see here in the bottom right, it says AS2 Loader. Same here, where I've already renamed the function. Based on that, we can see that there's a native code handler that gets loaded and it instantiates both of these functions to be called. What happens is AS2 and C handler,
11:42
if it's called with AS Native, will enter this function and zero will be kind of the index if it's AS Constructor, then one will be the index. And the entire interesting thing about this is that both of these functions, when they're called, they'll go through kind of an input sanitization
12:00
where they'll check to make sure they only have two arguments, and then they'll check to make sure that both arguments are either integers or can be coerced into integers. And then they end up calling a function. And this function is interesting in that it goes through a very large array, the array that I've renamed to AS2 Native Table.
12:21
And just by looking through this function, we're able to see where that array is and we're also able to get the size of the array because there's that comparison against hex 4a. Hex 4a ends up being the entire size of the array. And so if we look at it now, we have an array of a d-word, which ends up being that first argument to AS Native and AS Constructor.
12:41
And then we have the handler functions. And so going back to the ActionScript 2 we got from the SWF, we can see that if we're going to call, say, AS Native 100, that's going to go into the handler for AS, for 100, and then that second value is still unknown,
13:02
but that's going to vary for everything. Additionally, when you have the calls to AS Set Native and Set Native Accessor, the way these work is the first argument is going to be an object. The second argument is going to be the native code handler ID.
13:21
So it'd be like hex 65, hex 69, hex 29b, so on and so forth. After that is a comma separated string. And the comma separated string is going to start at zero or one, now I'm blanking, I think one, unless you have a optional fourth argument. If you have a fourth argument, like in that first call to AS Set Native here,
13:42
then it'll start at that value and then increment onward. And then for the native accessors you have getter and setter methods, so it'll actually jump by two. What I mean by that is for the second call, AS Set Native on O, O.Browse will end up being, it will go through the native code handler for 2205
14:02
and it'll have a method ID or value ID, whatever, of zero. Whereas for asset cache, asset cache.purge will start off at 206. And here's just a example of what the disassembly,
14:22
or what the decompilation ends up looking like. You have this method I being grabbed at the top and then you have a switch statement that kind of iterates through and acts differently based on that. Arguments are gonna be different and a lot of times zero was used for the constructors. A couple times 100 was used for constructors,
14:41
but it varies based on the proper, the API objects themselves. And none of that, as far as I know, is document anywhere. I just ended up calling it an AS2 arg structure. I only have it partially documented, but it's enough to be able to isolate where particular calls are going to end up in ActionScript 2 land.
15:03
And then looking at ActionScript 2 for, hopefully that's readable, for convolution filter, we can see that it's going to go through the native code handler for 1109 and it's going to be constructed by the case ID for zero. And it apparently inherits from bitmap filter
15:21
because its prototype is set to bitmap filter. And then it has a number of properties that are set all through AS set native accessor. 1109 is still the native code handler that it's going to go through. And it starts off at one. So matrix X will be method ID one and two,
15:43
and then matrix will be method ID five and six. And analysis of the bugs will show the exact code path and then analysis of the version right after will show how they patched it. And I'm not gonna go into that because that's not really why I'm trying to show this was just a good example to talk about ActionScript for.
16:02
But it's been very, very useful for making it very easy to do patch diffing, do bug analysis, all sorts of stuff without having to do normal bin diffing as that gets quite messy on Flash. But as I said, we were trying to look for an AS3 bug and do analysis on AS3, not on the AS2 bug.
16:23
So continuing on in our list of strings from earlier, we see another string match that looks very similar to the AS2 Swift match. So try and do the exact same trick. And we end up going, if we keep on walking the heads over and over again, up and up until we get a data reference to it, we end up with what I've renamed to built-in AS3 ABC data.
16:44
I now know that it's ABC data, but at the time I was a little lost. It didn't seem to have a format. I couldn't get any information about it. And even looking at how it was used in the binary was not the simplest. Thankfully, AVM Plus is open source.
17:01
And so I was able to look at core slash avm core.cpp and see the native initializer class. And as part of that, I ended up writing my own ActionScript byte code parser to iterate through this in its entirety. And I'm able to then map things.
17:20
Well, just using that, the AVM and ABC documentation was quite fantastic. But being able to reference the implementation itself was very, very helpful. Because the documentation is great, but implementation tells you exactly how it's actually being done. So looking at native initializer, we can see that there's this function,
17:42
or there's this initialization of the native initializer object. And then fill in classes is called, and then fill in methods is called. And both the arguments to fill in classes and fill in methods are values that are in the data section of the binary. And the built-in underscore AOT info is where the ActionScript byte code itself is.
18:03
So if we look at the assembly itself, we can see something that looks pretty similar. Actually, exactly similar. And using this, I'm able to find these methods, and then I'm able to start renaming things. One thing I noticed, and I didn't notice until a little bit later,
18:21
is that there's actually two sets of embedded ActionScript byte code. One that seems to be called built-in, and the other seems to be called shell underscore top level. Both of these are present in the AVM Plus source code. However, they do not match in the slightest, and none of the proprietary APIs are at all available in the open source implementation.
18:42
So convolution filter, for example, is not there. But everything that, all the methods that they use there to load everything and stand everything up still applies directly. And then here's just the shell top level one. And, okay, cool. So in order to parse the ActionScript byte code,
19:02
not the most complicated of formats, but there are several pools that you have to iterate through. So it starts off with constant pools. What this is is int, to int double, so on and so forth. Float has a star by it because it is optional. It's actually controlled within some pound defines,
19:21
and for whatever reason they don't have it at all, they've only opted for doubles. Following that is method information, which contains return types and parameter types and names. That I am grabbing. Constant pool I've mostly ignored except for the strings, namespace, namespace sets, and multinames. The metadata information I am completely ignoring.
19:42
I'm parsing it only so that I'm able to continue on to the next set. After that is instance information, and then class information, script information, and method body information. And I'm grabbing all of those. Method body information here is the one I'm using least out of, as I only really care about the traits for it and the method ID,
20:00
because that'll be vital when I actually map out what I'm seeing through the arrays to the functions that reference them. And then I mentioned traits in, I guess, all of these. Traits are things like trait getter, setter, method, class, const, stuff like that. Basically just extra properties on any of these elements.
20:23
Here's what the native class info looks like. Basically you have a function and then a class ID, and then the rest is not as important but is still very useful. I'm storing all of this data so that I can then later reference, and I'll kind of explain why later on. But just looking at some of the other arguments
20:43
to fill in classes, fill in methods, we're able to see the native class infrastructures. And it's just a very large array of that. That's the size of which is handled by the ActionScript bytecode but also by one of the arguments to the constructor to the native initializer constructor. And then following that is native method info,
21:01
which just consists of basically two function pointers followed by a method ID. And once again, parsing this all just to grab those method IDs so I can match things up later on. And here it is in the binary, pretty straightforward. All right, so going back to convolution filter,
21:21
we have some ActionScript bytecode but we don't exactly know what it looks like. I wrote an ActionScript bytecode parser and I did parse the method body information but I did not parse the instructions, I did not parse the exceptions. That got a little more involved than I really cared to do in Python.
21:41
Thankfully, there's a guy named Vladimir who goes by CyberShadow who wrote a tool called R-A-V-C-DASM, which is quite fantastic. It's what emitted the code at the top. So you can see that for the setter for the matrix property, it has a ref ID
22:00
of convolution filter instance matrix setter. It takes in an array and it returns nothing. The flag, hex 20, just specifies that this is a native function. Likewise, the getter for matrix X returns a number and has a flag, hex 20 as well. So if we look at the decompilation of the player global,
22:24
and for those who don't know, player global is a set of APIs that's released by Adobe every patch. It's available on their site, same page that you download the debugger projectors from. If you decompile those, you'll see that these functions are all marked as native and that the types all match up,
22:40
which is perfect. Always like to confirm that what I'm seeing and what I believe is actually true. On the left side, we have more output from R-A-V-C-DASM and on the right side, we have the decompilation from player global again. And so on the right side, we start off with a call to super and then we write this dot matrix X
23:01
by sending it to the value, the argument matrix X. And on the left side, kind of halfway through, you can see get local zero and then construct super zero so that matches. And then the next block right after that is get local zero, get local one, and then initialize the matrix X property. And all of that matches one to one and that's just great confirmation that what we're seeing is actually matching
23:21
what we believe it should be. One of the things I found just when poking around AVM Plus to try and basically try and write my parser, trying to make sure that everything I was writing actually matched up with how Adobe Flash was doing things was these pure methods, these call info structures.
23:44
And these are structures that exist both in the debug and the production or general availability builds of Flash. But in the debug build specifically, they end up being a little bit more interesting. They're defined with some macro gobbledygook. So like pure method, core adder, so on and so forth.
24:03
And if you look at pure method, that is then using another macro define call info. Define call info is conditionally defined on the definition of NJ underscore verbose. And if NJ verbose is true, is defined, then a name gets appended to the end of the structure,
24:24
which is quite fantastic because if we then look at that structure, we just have a pointer to an address, what ends up being a D word, another D word for the ACC set and then a pointer to a string. And that actually works out fantastically for some heuristics just looking for exactly that.
24:43
Just making sure all those values are sane and that you have an address to a function as well as an address, or yeah, a reference to a name and can end up with these call infrastructures and get even more information out just automatically. And it works fairly well.
25:01
Everything I was able to see that was defined in the code, I've been able to find in the binary itself as well as a few more that were not defined in the source, which is always awesome. So all in all, I was able to rename and find 208 call infrastructures. I actually end up renaming a lot more than that
25:22
as far as names go, but only because I'm also renaming the addresses as well, or the address of the structure as well. Going away from the convolution filter stuff and just looking at what my code does versus what other, what rabc-dasm does as well as player global. Up top we have a function definition from rabc-dasm
25:44
and it's for accessibility doc send event. And at the bottom we have my output. My output is pretty crappy. It's only really meant for me, which is why it's that bad right now. But kind of working at the middle and working, or starting at the middle and going our way in.
26:01
Starts off with optional false and if we look at the bottom we have optional false. Hex, or sorry, flag, hex 20 and then flag has optional. That's covered by the 40 because has optional is eight. And then it takes in a display object followed by two units and a boolean, which all that matches and then it returns a void.
26:24
And all of that seems to match what player global has. So all three match and just more further confirmation that the code I'm writing, the IDA Python that I have renaming things is actually on the right track and is making the right, is doing the right things.
26:42
So one of the last things I did probably a month and a half, maybe a month ago, was I have access because I am parsing all the class closures, because I'm parsing all the class structures. I have access to the class closure creation functions. Basically all the functions in AVM plus slash generated
27:03
that have the name create class closure. One of the functions, or one of the sets of functions that's incredibly useful to look at are the instance creation procedures, because all of these are where the V tables get set. And if you look at this code, it's fairly simple in that the first thing that really happens
27:22
is you take in the argument and then dereference it, get the IV table, dereference that and get the create instance proc and set that to something. And as I mentioned, CC underscore in my nomenclature is the class closure.
27:41
And I have access to those in my code. So just writing some extra heresics, I'm able to rename those. And I have 200 and something of them automatically renaming to the create instance procs. Just getting a little bit extra information. There are a bunch of them I'm not getting just because they're a little bit more complicated or there's some inheritance or host of reasons actually.
28:03
But it's still very, very helpful. So all in all, I have 77 addresses related to ActionScript 2 and those are only the 77 ActionScript native code handlers but then a lot more when it comes to ActionScript 3.
28:22
And there's probably more to be found but so far just with this, I'm able to massively simplify my reversing and triage efforts, which is quite, quite awesome. I was going to do a demo real quick but I think I'll actually say that for a couple more slides. So in December of 2015, Chalki had mentioned
28:43
that basically a lot of flash bugs that were being published were ActionScript 2 and not ActionScript 3. And that kind of has hold true for 2016 as well. I've seen a slight up rise in vulnerabilities in ActionScript 3, mostly seem to be found through fuzzing.
29:02
But I think a huge part of that is that ActionScript 3 is rather difficult to fuzz because of the type safety, do redefinition attacks again because of the type safety but also much harder to do analysis on. And part of the motivation for this was the fact that it's harder
29:21
but also because the monthly updates make it such a pain to do any sort of analysis. And I needed some way of just being able to take an IDB from scratch and have it just run and rename things and get myself back to a working state without having to do bin diffing and get knowledge from the previous month back in.
29:42
There's still a lot more work to be done and one of the things I was actually hoping to get done for this presentation was PDB generation. I've done some PDB work in the past. For example, March, sometime in 2015, Microsoft released symbols for NTDLL and NTOS kernel that did not have any of the symbols for,
30:01
or any of the type information for the PEB and TEB and so on and so forth. And I wrote some code that just stole it from a previous symbol and injected into the current. I currently have the ability to emit PDBs but still have some work to do before it actually ends up being fully useful.
30:21
But hopefully soon. And on that note, I am wondering Glitch, is there any initiative? And if you have any questions, please ask. I'm actually gonna try and show my code running which may not work with the projector but bear with me.
30:40
Also, thank you to Hexerays as I recently got a new Mac for analysis and whatnot. And it was, IDA was crashing on the latest version. Something to do with the touch bar and they were very, very quick and helpful about it. That'll just have to be readable enough.
31:00
All right, so if we look here, we see, let's say, byte array. There's nothing there. Only really just trying to show that I'm not really, I'm not faking things and loading an old IDB. Adobe Flash. All right, so it starts off by looking for the built-in AS3 ActionScript byte code
31:22
and then follows it up by looking for the shell top-level byte code. And then lastly, it does the ActionScript too. I'm also adding a decent number of types. Byte array. Okay, cool. So I now have all the byte array functions as well as anything else that may possibly use it.
31:43
So if I look at, let's look at this guy. This is basically the exact same code snippet that I showed earlier where I'm showing the create instance procedure from the class closure. But then also, if I go to any of these functions, I can get the type information that's going to go to them.
32:03
So in this particular case, I know that it's returning a void, it's a native function, and it takes in a rectangle and a byte array. And that's about it. Does anyone have any questions? If someone asks, I have a ZDI challenge coin in it for him.
32:23
Or if you just want one, ask. The question is, is it available on GitHub? Ah, sorry, I didn't mean to answer that. I do not have it available yet. I am planning on releasing it, but there is some code cleanup I need to do,
32:41
specifically around the hero six to find the, well, it's the, finding the create instance procedures is rather gross right now. But the worst part is finding the native initializer calls. I need to clean that up. I'm most likely going to clean up by just switching to unicorn and not doing it the way I'm currently doing.
33:10
Thank you very much.