先週の土曜日の勉強会で発表した資料を公開します。
FizzBuzz SWF Binary Golf on FlashLite 1.1
http://namazu.org/~takesako/swf/FizzBuzz-SWF-Golf.ppt
申し訳ないことにActionScriptの話は一つもでてきません。
SWFファイルの構造解析とASバイトコードの話です。
そんなシチュエーションがあるかどうかわかりませんが、
SWFファイルのバイナリを直接いじりたいときに役に立つのではないかと。
勉強会ではどの発表も面白かったのですが、個人的にはBeInteractive!のyossyさんとASバイトコードの話ができて嬉しかったです。
[お約束] SWF で FizzBuzz ってみた
とりあえず
(1) 正解のFizzBuzz文字列をそのまま出力した場合 -> 478 byte (FlashLite1.1)
http://namazu.org/~takesako/swf/fizz478.txt
(2) FizzBuzzを計算しながら出力した場合 -> 251 byte (FlashLite1.1)
http://namazu.org/~takesako/swf/fizz251.txt
(3) FizzBuzzを計算しながら出力した場合 -> 159 byte (FlashLite2.0)
http://namazu.org/~takesako/swf/fizz159.txt
ここまで圧縮できました。
ASバイトコード最適化
ASバイトコードの最適化の過程はこんな感じで
http://namazu.org/~takesako/swf/
--- fizz287.flm
+++ fizz161.flm
@@ -1,71 +1,48 @@
-movie 'fizz287.swf' // flash 4, total frames: 1, frame rate: 12 fps, 104x104 px
+movie 'fizz161.swf' compressed // flash 6, total frames: 1, frame rate: 12 fps, 104x104 px
frame 0
- push 'i', '0'
- setVariable
label1:
- push 'i', 'i'
+ push '100', 'i', 'i', 'i'
getVariable
increment
setVariable
- push '100', 'i'
getVariable
oldLessThan
- not
- not
branchIfTrue label6
- push 'x', 'x', 'x'
- getVariable
- push 'i'
+ push 'x', 'x'
getVariable
push 'i'
getVariable
push '15'
- divide
- int
- push '15'
- multiply
- subtract
+ modulo
branchIfTrue label2
push 'FizzBuzz'
branch label5
label2:
push 'i'
getVariable
- push 'i'
- getVariable
push '5'
- divide
- int
- push '5'
- multiply
- subtract
+ modulo
branchIfTrue label3
push 'Buzz'
branch label5
label3:
push 'i'
getVariable
- push 'i'
- getVariable
push '3'
- divide
- int
- push '3'
- multiply
- subtract
+ modulo
branchIfTrue label4
push 'Fizz'
branch label5
label4:
push 'i'
getVariable
label5:
concat
push ' '
concat
setVariable
branch label1
label6:
end // of frame 0
end
yossyさんから教えてもらったFlasmのコードでASバイトコードを読みやすい形に変換しています。
最後のFizzBuzz159byteへの圧縮は、ちょっとトリッキーなことをしています。
僕はActionScriptの経験は素人以下ですが、SWFバイナリの話ならできますので、
またどこかでAS関係のイベントがあれば声を掛けてくださると嬉しいです。(><)
この度は貴重な勉強会に参加できてよかったです。ありがとうございました。