<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-3811573850891467526</id><updated>2011-11-15T10:18:16.326-08:00</updated><category term='Lain'/><category term='jPSXdec'/><category term='Translation'/><category term='Playstation'/><title type='text'>psx h4x0rz in teh wired</title><subtitle type='html'>Ramblings about jPSXdec and the Lain Playstation game</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>35</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-6739456518374618203</id><published>2011-08-13T08:47:00.000-07:00</published><updated>2011-08-13T09:15:03.505-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Replicate</title><content type='html'>On a whim, I ran one of the unique identifiers in the Lain game through Google which led me to a couple interesting sites.&lt;br /&gt;&lt;br /&gt;A &lt;a href="http://lain.xq3.ru/"&gt;very impressive Russian site&lt;/a&gt; is trying to recreate most of the game's content for browsing on the web. What impressed me even more is the creator managed to reverse-engineer some of the game's data types before I did. He kindly gave jPSXdec a &lt;a href="http://lain.xq3.ru/about.html"&gt;shout out&lt;/a&gt; since it was used heavily to extract nearly everything on the site.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.geocities.co.jp/Playtown/3444/lain.html"&gt;This very old Japanese site&lt;/a&gt; I've seen before, but did a good job of documenting the game's content as well.&lt;br /&gt;&lt;br /&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-6739456518374618203?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/6739456518374618203/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2011/08/replicate.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6739456518374618203'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6739456518374618203'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2011/08/replicate.html' title='Replicate'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-8368696609412314440</id><published>2011-08-05T06:28:00.000-07:00</published><updated>2011-08-05T08:38:38.881-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><category scheme='http://www.blogger.com/atom/ns#' term='Translation'/><title type='text'>Translation Hacking</title><content type='html'>There's been a bit of activity with the translation lately, so I've been working more on the translation tools. Here's real video of the proof-of-concept I &lt;a href="http://jpsxdec.blogspot.com/2008/02/nihongo-niban.html"&gt;posted previously&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;iframe width="425" height="349" src="http://www.youtube.com/embed/T-9XW_OoCEQ" frameborder="0" allowfullscreen&gt;&lt;/iframe&gt;&lt;br /&gt;&lt;br /&gt;I figured it would be a bit rough to use this approach. Unfortunately, anything more than this would multiply the amount of work many times.&lt;br /&gt;&lt;br /&gt;I've also discovered there are 34 images on the game discs that don't seem to ever appear in the game. They're not particularly interesting, however.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/-iaay-APm1Z0/Tjvw-Utc7zI/AAAAAAAAASQ/cDqPLLHNC8I/s1600/LainUnused.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 400px; height: 314px;" src="http://3.bp.blogspot.com/-iaay-APm1Z0/Tjvw-Utc7zI/AAAAAAAAASQ/cDqPLLHNC8I/s400/LainUnused.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5637364312086212402" /&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-8368696609412314440?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/8368696609412314440/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2011/08/translation-hacking.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8368696609412314440'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8368696609412314440'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2011/08/translation-hacking.html' title='Translation Hacking'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://img.youtube.com/vi/T-9XW_OoCEQ/default.jpg' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-266374116795879159</id><published>2011-06-01T22:45:00.000-07:00</published><updated>2011-08-13T08:32:19.829-07:00</updated><title type='text'>Decoding MPEG-like bitstreams</title><content type='html'>&lt;p&gt;While developing jPSXdec for the last 4 years, I've run across three different methods of decoding bitstreams. Of course, in the honored tradition of multimedia hacking, none of these approaches are documented anywhere. So I thought I'd break that unwritten rule and actually write about them.&lt;/p&gt;&lt;p&gt;&lt;em&gt;If you'd like to learn more about what part this plays in MPEG and PlayStation .STR decoding, check out my thorough document on the subject: &lt;a href="http://code.google.com/p/jpsxdec/downloads/list"&gt;PlayStation_STR_format.txt&lt;/a&gt;&lt;/em&gt; &lt;/p&gt;&lt;h4&gt;Approach 1: Brute force&lt;/h4&gt;&lt;p&gt;This is the most obvious approach. For each code, peek the next n-bits until the bits match something.&lt;/p&gt;&lt;div class="codehilite" style="background: #181818; border: 1px solid silver; background: #141414; padding-left: 0.5em; word-wrap: normal; overflow-x: auto; overflow-y: hidden" markdown="1"&gt;&lt;pre&gt;&lt;code&gt;Next17Bits = Peek17Bits()&lt;br /&gt;For Each Possible Code&lt;br /&gt;    If Next17Bits starts with code bits&lt;br /&gt;        Skip bit code length&lt;br /&gt;        If END_OF_BLOCK code&lt;br /&gt;            return END_OF_BLOCK&lt;br /&gt;        Else If ESCAPE_CODE&lt;br /&gt;            ParseEscapeCode()&lt;br /&gt;        Else&lt;br /&gt;            return matching code&lt;br /&gt;        End If&lt;br /&gt;    End if&lt;br /&gt;Next&lt;br /&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;In the worst case, this approach requires 111 conditional checks to identify a bit code. To be honest, I've never actually seen this implemented anywhere besides by me years ago when first learning about bitstream parsing.&lt;/p&gt;&lt;h4&gt;Approach 2: Binary tree&lt;/h4&gt;&lt;p&gt;I actually ran across this approach implemented in the Serial Experiments Lain PlayStation game. You have a tree of conditionals testing the value of each bit until a match is found. &lt;/p&gt;&lt;div class="codehilite" style="background: #181818; border: 1px solid silver; background: #141414; padding-left: 0.5em; word-wrap: normal; overflow-x: auto; overflow-y: hidden" markdown="1"&gt;&lt;pre&gt;&lt;code&gt;If ReadNextBit() == '1'&lt;br /&gt;    If ReadNextBit() == '0'&lt;br /&gt;        return END_OF_BLOCK&lt;br /&gt;    Else&lt;br /&gt;        If ReadNextBit() == '0'&lt;br /&gt;            return ('11+0'.ZeroRun, '11+0'.AC)&lt;br /&gt;        Else&lt;br /&gt;            return ('11+1'.ZeroRun, '11+1'.AC)&lt;br /&gt;        End If&lt;br /&gt;    End If&lt;br /&gt;Else&lt;br /&gt;    If ReadNextBit() == '1'&lt;br /&gt;        If ReadNextBit() == '1'&lt;br /&gt;            // '011s'&lt;br /&gt;            ...&lt;br /&gt;        Else&lt;br /&gt;            // '010... and so on&lt;br /&gt;        End If&lt;br /&gt;    Else&lt;br /&gt;        // '00... and so on&lt;br /&gt;    End If&lt;br /&gt;End If&lt;br /&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;The branching can be optimized a bit for most leaves: once the length of the bit code is clear, the remaining bits can be used as the index in several small lookup tables. The jPSXdec implementation only requires (in the worst case) 12 branches to determine the longest bit codes.&lt;/p&gt;&lt;h4&gt;Approach 3: Array lookup&lt;/h4&gt;&lt;p&gt;I believe this type of approach is used in ffmpeg and the Q-gears decoder. Thanks to the unspoken tradition of never documenting anything, I was unable to understand what it was doing. It wasn't until I reverse-engineered the .iki bitstream parsing that I finally saw how this approach works.&lt;/p&gt;&lt;p&gt;At least for MPEG-1 (and PSX STR), you can take advantage of its particular set of variable length bit codes. Only the first code ('&lt;code&gt;11s&lt;/code&gt;') and the end-of-block code ('&lt;code&gt;10&lt;/code&gt;') need special parsing. The rest of the codes fall under one of three groups. The group a code belongs to can be determined by looking at how many initial zeros it has. &lt;/p&gt;&lt;ul&gt;&lt;li&gt;Group one starts with between 1 and 4 zeros (this also includes the escape code &lt;code&gt;000001&lt;/code&gt;). &lt;/li&gt;&lt;li&gt;Group two starts with between 6 and 8 zeros. &lt;/li&gt;&lt;li&gt;Group three starts with between 9 and 11 zeros. &lt;/li&gt;&lt;/ul&gt;&lt;p&gt;All codes in their groups:&lt;/p&gt;&lt;pre style="font-size: 80%"&gt;    [Special handling]&lt;br /&gt;    01 // end-of-block&lt;br /&gt;    11s&lt;br /&gt;    ---- [Group 1] ----&lt;br /&gt;    0 11s&lt;br /&gt;    0 100s&lt;br /&gt;    0 101s&lt;br /&gt;    0 0101s&lt;br /&gt;    0 0110s&lt;br /&gt;    0 0111s&lt;br /&gt;    0 00100s&lt;br /&gt;    0 00101s&lt;br /&gt;    0 00110s&lt;br /&gt;    0 00111s&lt;br /&gt;    0 000100s&lt;br /&gt;    0 000101s&lt;br /&gt;    0 000110s&lt;br /&gt;    0 000111s&lt;br /&gt;    0 00001 // escape code&lt;br /&gt;    0 0100000s&lt;br /&gt;    0 0100001s&lt;br /&gt;    0 0100010s&lt;br /&gt;    0 0100011s&lt;br /&gt;    0 0100100s&lt;br /&gt;    0 0100101s&lt;br /&gt;    0 0100110s&lt;br /&gt;    0 0100111s&lt;br /&gt;    ---- [Group 2] ----&lt;br /&gt;    000000 1000s&lt;br /&gt;    000000 1001s&lt;br /&gt;    000000 1010s&lt;br /&gt;    000000 1011s&lt;br /&gt;    000000 1100s&lt;br /&gt;    000000 1101s&lt;br /&gt;    000000 1110s&lt;br /&gt;    000000 1111s&lt;br /&gt;    000000 010000s&lt;br /&gt;    000000 010001s&lt;br /&gt;    000000 010010s&lt;br /&gt;    000000 010011s&lt;br /&gt;    000000 010100s&lt;br /&gt;    000000 010101s&lt;br /&gt;    000000 010110s&lt;br /&gt;    000000 010111s&lt;br /&gt;    000000 011000s&lt;br /&gt;    000000 011001s&lt;br /&gt;    000000 011010s&lt;br /&gt;    000000 011011s&lt;br /&gt;    000000 011100s&lt;br /&gt;    000000 011101s&lt;br /&gt;    000000 011110s&lt;br /&gt;    000000 011111s&lt;br /&gt;    000000 0010000s&lt;br /&gt;    000000 0010001s&lt;br /&gt;    000000 0010010s&lt;br /&gt;    000000 0010011s&lt;br /&gt;    000000 0010100s&lt;br /&gt;    000000 0010101s&lt;br /&gt;    000000 0010110s&lt;br /&gt;    000000 0010111s&lt;br /&gt;    000000 0011000s&lt;br /&gt;    000000 0011001s&lt;br /&gt;    000000 0011010s&lt;br /&gt;    000000 0011011s&lt;br /&gt;    000000 0011100s&lt;br /&gt;    000000 0011101s&lt;br /&gt;    000000 0011110s&lt;br /&gt;    000000 0011111s&lt;br /&gt;    ---- [Group 3] ----&lt;br /&gt;    000000000 10000s&lt;br /&gt;    000000000 10001s&lt;br /&gt;    000000000 10010s&lt;br /&gt;    000000000 10011s&lt;br /&gt;    000000000 10100s&lt;br /&gt;    000000000 10101s&lt;br /&gt;    000000000 10110s&lt;br /&gt;    000000000 10111s&lt;br /&gt;    000000000 11000s&lt;br /&gt;    000000000 11001s&lt;br /&gt;    000000000 11010s&lt;br /&gt;    000000000 11011s&lt;br /&gt;    000000000 11100s&lt;br /&gt;    000000000 11101s&lt;br /&gt;    000000000 11110s&lt;br /&gt;    000000000 11111s&lt;br /&gt;    000000000 010000s&lt;br /&gt;    000000000 010001s&lt;br /&gt;    000000000 010010s&lt;br /&gt;    000000000 010011s&lt;br /&gt;    000000000 010100s&lt;br /&gt;    000000000 010101s&lt;br /&gt;    000000000 010110s&lt;br /&gt;    000000000 010111s&lt;br /&gt;    000000000 011000s&lt;br /&gt;    000000000 011001s&lt;br /&gt;    000000000 011010s&lt;br /&gt;    000000000 011011s&lt;br /&gt;    000000000 011100s&lt;br /&gt;    000000000 011101s&lt;br /&gt;    000000000 011110s&lt;br /&gt;    000000000 011111s&lt;br /&gt;    000000000 0010000s&lt;br /&gt;    000000000 0010001s&lt;br /&gt;    000000000 0010010s&lt;br /&gt;    000000000 0010011s&lt;br /&gt;    000000000 0010100s&lt;br /&gt;    000000000 0010101s&lt;br /&gt;    000000000 0010110s&lt;br /&gt;    000000000 0010111s&lt;br /&gt;    000000000 0011000s&lt;br /&gt;    000000000 0011001s&lt;br /&gt;    000000000 0011010s&lt;br /&gt;    000000000 0011011s&lt;br /&gt;    000000000 0011100s&lt;br /&gt;    000000000 0011101s&lt;br /&gt;    000000000 0011110s&lt;br /&gt;    000000000 0011111s&lt;br /&gt;&lt;/pre&gt;&lt;p&gt;Each group has its own lookup table of 256 entries, and each code will be associated with one or more entries in the lookup table. After stripping off the minimum number of zeros in the group, no entry in the group will have more than 8 bits remaining in the bit code. For codes that have 8 bits remaining, its value identifies the associated table index. For the bit codes that have fewer than 8 bits remaining, you have to walk through every combination of the remaining bits to find all associated indexes.&lt;/p&gt;&lt;p&gt;Example:&lt;div markdown="1" style="margin-left: 3em"&gt;Group 1 code: 00110s&lt;br /&gt;Use 0 for sign bit for now: 001100&lt;br /&gt;Strip off first leading 0: 01100&lt;br /&gt;Find all combinations of remaining bits:&lt;/p&gt;&lt;pre&gt;&lt;code&gt;    01100+000 = 96 (table index)&lt;br /&gt;    01100+001 = 97&lt;br /&gt;    01100+010 = 98&lt;br /&gt;    01100+011 = 99&lt;br /&gt;    01100+100 = 100&lt;br /&gt;    01100+101 = 101&lt;br /&gt;    01100+110 = 102&lt;br /&gt;    01100+111 = 103&lt;br /&gt;&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Thus bit code 00110s will be associated with table indexes 96-103.&lt;/div&gt;&lt;/p&gt;&lt;p&gt;Now each table entry needs three values: the inverse discreet cosine transform (IDCT) run of zero-value alternating current (AC) coefficients, the non-zero AC coefficient value, and the length of the bitstream bits that should be skipped.&lt;/p&gt;&lt;p&gt;Once all three tables are constructed, the following pseudo code will parse your bitstream.&lt;/p&gt;&lt;div class="codehilite" style="background: #181818; border: 1px solid silver; background: #141414; padding-left: 0.5em; word-wrap: normal; overflow-x: auto; overflow-y: hidden" markdown="1"&gt;&lt;pre&gt;&lt;code&gt;If ReadNextBit() == '1'&lt;br /&gt;    If ReadNextBit() == '0'&lt;br /&gt;        return END_OF_BLOCK&lt;br /&gt;    Else&lt;br /&gt;        If ReadNextBit() == '0'&lt;br /&gt;            return ('11+0'.ZeroRun, '11+0'.AC)&lt;br /&gt;        Else&lt;br /&gt;            return ('11+1'.ZeroRun, '11+1'.AC)&lt;br /&gt;        End If&lt;br /&gt;    End If&lt;br /&gt;Else&lt;br /&gt;    Next16Bits = Peek16Bits()&lt;br /&gt;    If NumberOfLeadingZeros(Next16Bits) &amp;lt;= 4&lt;br /&gt;        Match = LookupTable1[(Next16Bits &amp;gt;&amp;gt; 8) &amp;amp; 0xff]&lt;br /&gt;    Else If NumberOfLeadingZeros(Next16Bits) &amp;lt;= 8&lt;br /&gt;        Match = LookupTable2[(Next16Bits &amp;gt;&amp;gt; 3) &amp;amp; 0xff]&lt;br /&gt;    Else If NumberOfLeadingZeros(Next16Bits) &amp;lt;= 11&lt;br /&gt;        Match = LookupTable3[Next16Bits &amp;amp; 0xff]&lt;br /&gt;    Else&lt;br /&gt;        // bitstream error&lt;br /&gt;    End If&lt;br /&gt;    If Match == ESCAPE_CODE&lt;br /&gt;        SkipBits(ESCAPE_CODE.BitLength)&lt;br /&gt;        ParseEscapeCode()&lt;br /&gt;    Else&lt;br /&gt;        SkipBits(Match.BitLength)&lt;br /&gt;        return (Match.ZeroRun, Match.AC)&lt;br /&gt;    End If&lt;br /&gt;End If&lt;br /&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Of course the implementation details can vary, but this gives the idea. The Approach 3 I implemented for jPSXdec requires about 8 conditionals to identify a bit code in the worst case. I've found it to be about 10%-15% faster than the Approach 2 I've been using.&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-266374116795879159?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/266374116795879159/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2011/06/decoding-mpeg-like-bitstreams.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/266374116795879159'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/266374116795879159'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2011/06/decoding-mpeg-like-bitstreams.html' title='Decoding MPEG-like bitstreams'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-7151783890535665196</id><published>2010-09-06T14:33:00.000-07:00</published><updated>2011-07-25T13:08:40.140-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Playstation'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>PlayStation Video Decoders:The Final Showdown</title><content type='html'>Updated from the &lt;a href="http://jpsxdec.blogspot.com/2009/10/psx-video-converter-deathmatch.html"&gt;previous comparison&lt;/a&gt; with the lastest versions, and three new decoders!&lt;br /&gt;&lt;br /&gt;Most importantly, I finally captured what it &lt;strong&gt;ACTUALLY&lt;/strong&gt; looks like on PlayStation hardware (in the dead center).&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_vrkdqnCR4Dk/TIsinAdbLpI/AAAAAAAAARk/vySpxP4X7EU/s1600/G_INFO_STR-all-side-by-side.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 296px; height: 400px;" src="http://1.bp.blogspot.com/_vrkdqnCR4Dk/TIsinAdbLpI/AAAAAAAAARk/vySpxP4X7EU/s400/G_INFO_STR-all-side-by-side.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5515540222178963090" /&gt;&lt;/a&gt;Those on top get it (more) correct, those on the bottom get it (more) wrong (and ffmpeg and Q-gears are just weird).&lt;br /&gt;&lt;br /&gt;Naturally jPSXdec dominates in quality and accuracy. :)&lt;br /&gt;&lt;!-- &lt;br /&gt;I'm particularly amused by the failure of the new reevengi decoder because its author is under the impression it is "&lt;a href="http://z4.invisionfree.com/Resident_Evil_1_2_3/index.php?s=c8e331e217513bdad593af53215705a9&amp;amp;showtopic=97&amp;view=findpost&amp;p=2400636"&gt;more advanced&lt;/a&gt;" than jPSXdec (due to the fact it uses OpenGL, or is written in "&lt;a href="http://www.parashift.com/c++-faq-lite/how-to-post.html#faq-5.4"&gt;C/++&lt;/a&gt;", or something...).&lt;br /&gt;&lt;br /&gt;I was also kinda bummed that the MAME team didn't respond to my offer to help improve their PlayStation MDEC accuracy. Given MAME's philosophy of precise replication of actual hardware, I thought they would welcome it.&lt;br /&gt;--&gt;&lt;br /&gt;The lineup:&lt;ul&gt;&lt;li&gt;&lt;a href="http://www.zophar.net/utilities/psxutil/psxplay.html"&gt;PSXPlay&lt;/a&gt;&lt;/li&gt;&lt;li&gt;a fixed version of PCSX by Gabriele Gorla&lt;/li&gt;&lt;li&gt;&lt;a href="http://kenai.com/projects/jpsxdec"&gt;jPSXdec&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://mamedev.org/"&gt;MAME&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://homepage2.nifty.com/~mkb/PsxMC/"&gt;PsxMC&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://www.zophar.net/utilities/psxutil/psmplay.html"&gt;PSmplay&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://come.to/psxtulz"&gt;PsxTulz&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://pmandin.atari.org/dotclear/index.php?2008/12/28/21-en-perso-engines-reevengi"&gt;reevengi&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://www.pcsx.net/"&gt;PCSX&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://ffmpeg.org/"&gt;ffmeg&lt;/a&gt;&lt;/li&gt;&lt;li&gt;&lt;a href="http://q-gears.svn.sourceforge.net/viewvc/q-gears/branches/ogre_qgears/src/common/movie/decoders"&gt;Q-gears&lt;/a&gt;&lt;/li&gt;&lt;/ul&gt;See the &lt;a href="https://sites.google.com/site/lainpsxfiles/a/psx-video-deathmatch-20100906.zip"&gt;download&lt;/a&gt; for all the jucy (and technical) details.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-7151783890535665196?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/7151783890535665196/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2010/09/psx-video-decoders-final-showdown.html#comment-form' title='9 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7151783890535665196'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7151783890535665196'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2010/09/psx-video-decoders-final-showdown.html' title='&lt;center&gt;PlayStation Video Decoders:&lt;br&gt;The Final Showdown&lt;/center&gt;'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_vrkdqnCR4Dk/TIsinAdbLpI/AAAAAAAAARk/vySpxP4X7EU/s72-c/G_INFO_STR-all-side-by-side.png' height='72' width='72'/><thr:total>9</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-9194223144575440375</id><published>2010-08-19T12:39:00.000-07:00</published><updated>2010-09-10T23:31:41.871-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Immaculate Decoding</title><content type='html'>Just writing a straight-forward PlayStation 1 video decoder has been a lot of work. However, for the absolute most impeccable quality, there is so much more that can be considered in the process.&lt;br /&gt;&lt;h4&gt;Upsampling&lt;/h4&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/TG2KzrZweeI/AAAAAAAAAQI/lfd9SRW4toY/s1600/YCbCrBreakdown.png"&gt;&lt;img style="float:right; margin:0 0 10px 10px;cursor:pointer; cursor:hand;width: 200px; height: 178px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/TG2KzrZweeI/AAAAAAAAAQI/lfd9SRW4toY/s200/YCbCrBreakdown.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5507210539772705250" /&gt;&lt;/a&gt;When PlayStation videos are created, the pixels are broken up into luma (brightness) components and chroma (color) components. Like with JPEG and MPEG formats, 3/4 of the chroma information is thrown away because the human eye can't really tell (this is an example of lossy compression).&lt;br /&gt;&lt;br /&gt;When decoding, that lost chroma information needs to be recreated somehow to convert the pixels back into RGB. Unfortunately there is no one 'right' way to do it, because there's really no way to get that lost information back. All you can do is 'guess' by filling in the blanks based on the information around the pixels using some kind of interpolation. Some of the most well known kinds of interpolation are: nearest neighbor, bilinear, bicubic, and lanczos. I've read about more advanced chroma upsampling approaches that also take into account the luma component. This works because there is often a lot of correlation between the luma and chroma components--when the luma changes, the chroma probably will also. I'd like to try to find the best one, but I haven't had much luck on finding many good resources about them all.&lt;br /&gt;&lt;br /&gt;Now, because this is essentially just scaling of a 2D image, I've been worried about &lt;a href="http://www.4p8.com/eric.brasseur/gamma.html"&gt;this article&lt;/a&gt; that points out a nasty little gremlin called gamma correction. It seems nearly everyone has been doing image scaling wrong since the popularization of the sRGB gamma corrected color space. I'm assuming video isn't immune to the same problem, yet I've never seen anyone mention it.&lt;br /&gt;&lt;h4&gt;Deblocking&lt;/h4&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://en.wikipedia.org/wiki/Compression_artifact"&gt;&lt;img style="float:left; margin:0 10px 10px 0;cursor:pointer; cursor:hand;width: 150px; height: 180px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/TG2MLwMzm5I/AAAAAAAAAQ4/GNfL3WAZiMw/s200/Sego_lily_cm-150.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5507212052889050002" /&gt;&lt;/a&gt;Assuming we find the upsampling method of choice, there are still ways the image can be improved. Most video codecs break the frames down into 'blocks', then encode each block separately--again losing information along the way. When everything is reconstructed, that lost information can often be seen as &lt;a href="http://en.wikipedia.org/wiki/Compression_artifact"&gt;visible distortions between blocks&lt;/a&gt;. This problem has been addressed in more recent video codecs such as h.264, but is still a problem with the older MPEG2. I believe nearly all DVD players do some deblocking before showing the final frame.&lt;br /&gt;&lt;br /&gt;Even though MPEG2 has been around a long time and deblocking is so common, I've had the darndest time trying to find much mention of what deblocking algorithms are in use today. &lt;a href="http://www.assassinationscience.com/johncostella/unblock/"&gt;UnBlock&lt;/a&gt;, and this page on &lt;a href="http://www.utdallas.edu/~aria/mcl/post/"&gt;JPEG Post-Processing&lt;/a&gt; are the best I've come by. I think I've read somewhere that some advanced deblockers can even make use of the original MPEG2 data to improve the deblocking.&lt;br /&gt;&lt;br /&gt;I still consider myself a multimedia novice, so there are probably more post-processing methods that would really make the output shine. A big bummer among all research in that area is that if you can think it, you can pretty much count on it been patented.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Given how difficult all this stuff is, I really &lt;em&gt;really&lt;/em&gt; wish I could just pass that problem off to the big players in the field, such as ffmpeg (i.e. libavcodec). I've even considered writing a PSX video to MPEG2 video translator so the MPEG2 video can be fed into ffmpeg. Unfortunately there are some big reasons why doing this still makes me uneasy.&lt;br /&gt;&lt;h4&gt;IDCT&lt;/h4&gt;The PlayStation uses its own particular IDCT approach that I've never seen anywhere else. Given how important it is that the &lt;a href="http://guru.multimedia.cx/the-mpeg124-and-h26123-idct/"&gt;DCT used to encode the video matches the IDCT used to decode&lt;/a&gt;, there are no existing decoders that can do it (except jPSXdec of course). &lt;br /&gt;&lt;h4&gt;Differences in YCbCr&lt;/h4&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_vrkdqnCR4Dk/TG2LWhIZcLI/AAAAAAAAAQQ/jtaAy28YxVI/s1600/ChromaPlacement.png"&gt;&lt;img style="float:right; margin:0 0 10px 10px;cursor:pointer; cursor:hand;width: 200px; height: 116px;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/TG2LWhIZcLI/AAAAAAAAAQQ/jtaAy28YxVI/s200/ChromaPlacement.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5507211138310959282" /&gt;&lt;/a&gt;Another worry is that a &lt;strong&gt;real&lt;/strong&gt; good quality MPEG2 decoder will spatially position the chroma components in the proper location (vertically aligned with every other luma component) as opposed to how I believe PSX does it (the MPEG1 way: in-between luma components).&lt;br /&gt;&lt;br /&gt;To make things a bit more complicated, MPEG2 uses the proper Rec.601 Y'CbCr color space with [16-235] luma, and [16-240] chroma range. PSX on the other hand, uses the full [0-255] range for color information. Many video converters don't handle that discrepancy very well. Related to that, pretty much all converters store the data as integers, so any fractional information is lost after every conversion. In contrast, jPSXdec maintains all that fractional information until the very end.&lt;br /&gt;&lt;br /&gt;In general though, I have &lt;a href="http://jpsxdec.blogspot.com/2010/03/ycbcr-rgb-showdown.html"&gt;not been impressed with ffmpeg's quality&lt;/a&gt;, so I can't suggest people use it when looking for good quality.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;One advantage that comes when incorporating all these enhancements in jPSXdec is it provides a much nicer user experience. No need to be hopping between multiple tools to get the best results. &lt;br /&gt;&lt;br /&gt;So if I were to actually implement all these features, where would I get the information I lack? Perhaps the &lt;a href="http://www.doom9.org/"&gt;doom9.org forums&lt;/a&gt; could help. If any multimedia gurus happen to pass by this post, please, if you could, toss some wisdom my way.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-9194223144575440375?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/9194223144575440375/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2010/08/immaculate-decoding.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/9194223144575440375'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/9194223144575440375'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2010/08/immaculate-decoding.html' title='Immaculate Decoding'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_vrkdqnCR4Dk/TG2KzrZweeI/AAAAAAAAAQI/lfd9SRW4toY/s72-c/YCbCrBreakdown.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-2750222333733142465</id><published>2010-03-26T19:34:00.000-07:00</published><updated>2010-06-10T06:54:36.245-07:00</updated><title type='text'>YCbCr to RGB Conversion Showdown</title><content type='html'>In trying to ensure pixel perfect accuracy in my color conversions, I wanted to compare how two popular video converters handle YCbCr to RGB conversion: &lt;a href="http://ffmpeg.org/"&gt;ffmpeg&lt;/a&gt;* and &lt;a href="http://www.virtualdub.org/"&gt;VirtualDub&lt;/a&gt; v1.9.8.&lt;br /&gt;&lt;br /&gt;The Rec.601 YCbCr to RGB equation is defined as such:&lt;blockquote&gt;Given Y color range of [16, 235] and Cb,Cr color range of [16, 240].&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;[ 1.164   0       1.59  ]   [ Y  - 16  ]     [ r ]&lt;br /&gt;[ 1.164  -0.391  -0.813 ] * [ Cb - 128 ]  =  [ g ]&lt;br /&gt;[ 1.164   2.018   0     ]   [ Cr - 128 ]     [ b ]&lt;/pre&gt;&lt;/blockquote&gt;&lt;br /&gt;You can generate a table of the YCbCr to RGB conversion using this bit of code. Values outside valid YCbCr ranges are simply mapped to white.&lt;br /&gt;&lt;pre style="font-size:80%"&gt;&lt;br /&gt;public class YCbCrAndRgb {&lt;br /&gt;    public static void main(String[] args) {&lt;br /&gt;        for (int y = 0; y &lt; 256; y++) {&lt;br /&gt;            for (int cb = 0; cb &lt; 256; cb++) {&lt;br /&gt;                for (int cr = 0; cr &lt; 256; cr++) {&lt;br /&gt;                    if (y &gt;=  16 &amp;&amp; cb &gt;=  16 &amp;&amp; cr &gt;= 16 &amp;&amp;&lt;br /&gt;                        y &lt;= 235 &amp;&amp; cb &lt;= 240 &amp;&amp; cr &lt;= 240) &lt;br /&gt;                    {&lt;br /&gt;                        int r = (int)Math.round( (y - 16) * 1.164                       + (cr - 128) *  1.596 );&lt;br /&gt;                        int g = (int)Math.round( (y - 16) * 1.164 + (cb - 128) * -0.391 + (cr - 128) * -0.813 );&lt;br /&gt;                        int b = (int)Math.round( (y - 16) * 1.164 + (cb - 128) *  2.018                       );&lt;br /&gt;                        &lt;br /&gt;                        if (r &lt; 0) r = 0; else if (r &gt; 255) r = 255;&lt;br /&gt;                        if (g &lt; 0) g = 0; else if (g &gt; 255) g = 255;&lt;br /&gt;                        if (b &lt; 0) b = 0; else if (b &gt; 255) b = 255;&lt;br /&gt;                        &lt;br /&gt;                        System.out.format("%02x%02x%02x\t%02x%02x%02x", y, cb, cr, r, g, b);&lt;br /&gt;                        System.out.println();&lt;br /&gt;                    } else {&lt;br /&gt;                        System.out.format("%02x%02x%02x\tffffff", y, cb, cr);&lt;br /&gt;                        System.out.println();&lt;br /&gt;                    }&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;br /&gt;Using a pixel format without subsampling should let me convert pixels without blending interfering, however &lt;a href="https://roundup.ffmpeg.org/issue1820"&gt;ffmpeg still adds blending even to 4:4:4&lt;/a&gt;, which would distort the results. So instead I generated several AVIs with small dimensions (8x8) with &lt;a href="http://www.fourcc.org/yuv.php#YV12"&gt;fourcc YV12&lt;/a&gt; pixel format (4:2:0), each frame containing one solid color. That came out to 256 AVI files, each with 256*256 frames. &lt;br /&gt;&lt;br /&gt;Those AVIs were fed through ffmpeg and VirtualDub and converted to uncompressed RGB AVIs. This ffmepg command converts YCbCr to RGB AVI.&lt;pre style="font-size:80%"&gt;ffmpeg -i inYCbCr.avi -vcodec rawvideo -pix_fmt bgr24 outRgb.avi&lt;/pre&gt;Under VirtualDub's Video-&amp;gt;Color Depth menu you can set the output pixel format.&lt;br /&gt;&lt;br /&gt;A little script walked through every AVI and pulled out the first RGB pixel of each frame and associated it with the original YCbCr color.&lt;br /&gt;&lt;br /&gt;At that point I had a table with 256^3 rows and 4 columns:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Original YCbCr color&lt;/li&gt;&lt;li&gt;RGB generated with the standard equation and floating-point math&lt;/li&gt;&lt;li&gt;RGB generated with VirtualDub&lt;/li&gt;&lt;li&gt;RGB generated with ffmpeg&lt;/li&gt;&lt;/ol&gt;Here you can download 4096x4096 images of the resulting RGB values using the three conversion methods.&lt;br /&gt;&lt;br /&gt;&lt;table style="text-align: center"&gt;&lt;tr&gt;&lt;td colspan="2"&gt;Floating-point&lt;br /&gt;&lt;a href="http://sites.google.com/site/lainpsxfiles/a/ycbcr2rgb-myfloat.png?attredirects=0"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 200px; height: 200px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/S61wDU_1njI/AAAAAAAAAPA/1vjdoabGsAY/s200/ycbcr2rgb-myfloat.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5453137926293921330" /&gt;&lt;/a&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td&gt;VirtualDub&lt;br /&gt;&lt;a href="http://sites.google.com/site/lainpsxfiles/a/ycbcr2rgb-virtualdub.png?attredirects=0"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 200px; height: 200px;" src="http://1.bp.blogspot.com/_vrkdqnCR4Dk/S61wWr1PoBI/AAAAAAAAAPQ/EjIXEwjeUaM/s200/ycbcr2rgb-virtualdub.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5453138258841018386" /&gt;&lt;/a&gt;&lt;/td&gt;&lt;td&gt;ffmpeg&lt;br /&gt;&lt;a href="http://sites.google.com/site/lainpsxfiles/a/ycbcr2rgb-ffmpeg.png?attredirects=0"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 200px; height: 200px;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/S61xccPizvI/AAAAAAAAAPY/BmoZKTymUQQ/s200/ycbcr2rgb-ffmpeg.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5453139457247203058" /&gt;&lt;/a&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;Now to analyze, starting with some visual comparisons. Diffing and autoleveling (normalizing) exposes what pixels are different.&lt;br /&gt;&lt;br /&gt;&lt;table style="text-align: center"&gt;&lt;tr&gt;&lt;td&gt;Floating-point vs. VirtualDub&lt;br /&gt;&lt;a href="http://sites.google.com/site/lainpsxfiles/a/myfloat-vs-virtualdub.png?attredirects=0"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 200px; height: 200px;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/S617Yh8dmVI/AAAAAAAAAPg/JzFriYzW_Qw/s200/myfloat-vs-virtualdub.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5453150385174583634" /&gt;&lt;/a&gt;&lt;/td&gt;&lt;td&gt;Floating-point vs. ffmpeg&lt;br /&gt;&lt;a href="http://sites.google.com/site/lainpsxfiles/a/myfloat-vs-ffmpeg.png?attredirects=0"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 200px; height: 200px;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/S617oGtLPnI/AAAAAAAAAPo/BRa6Yvp-hAY/s200/myfloat-vs-ffmpeg.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5453150652740615794" /&gt;&lt;/a&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;Seems VirtualDub is far more accurate than ffmepg, but still doesn't match the floating-point version perfectly.&lt;br /&gt;&lt;br /&gt;Now some numbers.&lt;ul&gt;&lt;li&gt;VirtualDub has 1795792 pixels (11%) different from the floating-point conversion.&lt;/li&gt;&lt;li&gt;ffmpeg has 10827725 pixels (65%) different from the floating-point conversion.&lt;/li&gt;&lt;/ul&gt;Differences broken down by color channel.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/S61_Vd_pnuI/AAAAAAAAAPw/iGwvQ5Bl6Fc/s1600/ycbcr-stats.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 200px; height: 136px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/S61_Vd_pnuI/AAAAAAAAAPw/iGwvQ5Bl6Fc/s200/ycbcr-stats.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5453154730621116130" /&gt;&lt;/a&gt;I'm disappointed but not surprised that there are so many 1-off values in general. But ffmpeg's variance is as much as -3?? Wow, I hope I'm doing something wrong because that's pretty bad.&lt;br /&gt;&lt;br /&gt;In the rare case someone has over an hour and 10GB to spare, along with various strange prerequisites, you can &lt;a href="http://sites.google.com/site/lainpsxfiles/a/YCbCr-compare.zip?attredirects=0&amp;d=1"&gt;download the scripts&lt;/a&gt; used to generate these details.&lt;br /&gt;&lt;br /&gt;&lt;div style="float:left"&gt;*&lt;/div&gt;&lt;pre style="font-size:60%"&gt;FFmpeg version SVN-r22107, Copyright (c) 2000-2010 the FFmpeg developers&lt;br /&gt;  built on Feb 28 2010 06:11:15 with gcc 4.4.2&lt;br /&gt;  configuration: --enable-memalign-hack --cross-prefix=i686-mingw32- --cc=ccache-i686-mingw32-gcc --&lt;br /&gt;arch=i686 --target-os=mingw32 --enable-runtime-cpudetect --enable-avisynth --enable-gpl --enable-ver&lt;br /&gt;sion3 --enable-bzlib --enable-libgsm --enable-libfaad --enable-pthreads --enable-libvorbis --enable-&lt;br /&gt;libtheora --enable-libspeex --enable-libmp3lame --enable-libopenjpeg --enable-libxvid --enable-libsc&lt;br /&gt;hroedinger --enable-libx264 --enable-libopencore_amrwb --enable-libopencore_amrnb&lt;br /&gt;  libavutil     50. 9. 0 / 50. 9. 0&lt;br /&gt;  libavcodec    52.55. 0 / 52.55. 0&lt;br /&gt;  libavformat   52.54. 0 / 52.54. 0&lt;br /&gt;  libavdevice   52. 2. 0 / 52. 2. 0&lt;br /&gt;  libswscale     0.10. 0 /  0.10. 0&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-2750222333733142465?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/2750222333733142465/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2010/03/ycbcr-rgb-showdown.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/2750222333733142465'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/2750222333733142465'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2010/03/ycbcr-rgb-showdown.html' title='YCbCr to RGB Conversion Showdown'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_vrkdqnCR4Dk/S61wDU_1njI/AAAAAAAAAPA/1vjdoabGsAY/s72-c/ycbcr2rgb-myfloat.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-3210957696854157880</id><published>2010-03-13T00:00:00.000-08:00</published><updated>2010-04-18T13:01:07.982-07:00</updated><title type='text'>IDCT Demystified (a little)</title><content type='html'>The inverse discrete cosine transform is a very mysterious and intimidating equation. &lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_vrkdqnCR4Dk/S5tGlBsBbBI/AAAAAAAAALQ/9p5WDxPsFwo/s1600-h/idctequation.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 400px; height: 262px;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/S5tGlBsBbBI/AAAAAAAAALQ/9p5WDxPsFwo/s400/idctequation.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5448025776156929042" /&gt;&lt;/a&gt;(apologies if I messed up the notation)&lt;br /&gt;&lt;br /&gt;For the longest time I let the IDCT remain a black box. I found a handful of Java IDCT implementations, plugged them in, and cross my fingers.&lt;br /&gt;&lt;br /&gt;I know what the 2D DCT does: it pushes all the image data to the top left corner of the block, while the IDCT undoes that magic. I'm not sure &lt;i&gt;how&lt;/i&gt; it does this, but just knowing &lt;i&gt;what&lt;/i&gt; it does is enough for me.&lt;br /&gt;&lt;br /&gt;But recently I finally discovered that the IDCT is simply a couple of matrix multiplications. &lt;br /&gt;&lt;br /&gt;&lt;i&gt;idct_matrix&lt;sup&gt;T&lt;/sup&gt; . coefficients . idct_matrix&lt;/i&gt;&lt;br /&gt;&lt;br /&gt;The IDCT equation doesn't really suggest that to the casual mathematician. Of course if you take a class or pay for a book on the subject, maybe this is old news to you.&lt;br /&gt;&lt;br /&gt;For those uninformed like me, let's take a closer look at this IDCT matrix.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_vrkdqnCR4Dk/S5tGdVqxI1I/AAAAAAAAALI/bJkHq2n6pNg/s1600-h/idctplain.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 400px; height: 347px;" src="http://4.bp.blogspot.com/_vrkdqnCR4Dk/S5tGdVqxI1I/AAAAAAAAALI/bJkHq2n6pNg/s400/idctplain.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5448025644081423186" /&gt;&lt;/a&gt;&lt;br /&gt;Theoretically we could throw a bunch of trigonometry identities at this matrix to simplify it, but it turns out to be so much easier to just calculate it and see which decimal values are the same. In the end, there turns out to only be 7 unique values (listed here in varying forms).&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;1/sqrt(8)       =  cos(  PI/ 4)/2&lt;br /&gt;cos(1*PI/16)/2  =  cos(  PI/16)/2  =  sqrt(2+sqrt(2+sqrt(2)))/4&lt;br /&gt;cos(2*PI/16)/2  =  cos(  PI/ 8)/2  =  sqrt(2+sqrt(2))/4&lt;br /&gt;cos(3*PI/16)/2  =  cos(3*PI/16)/2  =  sqrt(2+sqrt(2-sqrt(2)))/4&lt;br /&gt;cos(5*PI/16)/2  =  cos(5*PI/16)/2  =  sqrt(2-sqrt(2-sqrt(2)))/4&lt;br /&gt;cos(6*PI/16)/2  =  cos(3*PI/ 8)/2  =  sqrt(2-sqrt(2))/4&lt;br /&gt;cos(7*PI/16)/2  =  cos(7*PI/16)/2  =  sqrt(2-sqrt(2+sqrt(2)))/4&lt;/pre&gt;Now the IDCT matrix can be simplified to this:&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_vrkdqnCR4Dk/S5tGwFKPYVI/AAAAAAAAALY/rXqNVG1SztQ/s1600-h/idctmatrix.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 400px; height: 346px;" src="http://1.bp.blogspot.com/_vrkdqnCR4Dk/S5tGwFKPYVI/AAAAAAAAALY/rXqNVG1SztQ/s400/idctmatrix.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5448025966067540306" /&gt;&lt;/a&gt;Taking things a step further, let's multiply the two IDCT matrix multiplications out (&lt;a href="http://maxima.sourceforge.net/"&gt;Maxima&lt;/a&gt; is awesome). After a lot of trigonometric simplification, it turns into a massive matrix. This tiny portion below resembles what the entire matrix looks like.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_vrkdqnCR4Dk/S5tOHVxwVGI/AAAAAAAAAO4/ehdNkDh1AGo/s1600-h/idctmultiplied-summary.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 400px; height: 108px;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/S5tOHVxwVGI/AAAAAAAAAO4/ehdNkDh1AGo/s400/idctmultiplied-summary.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5448034062246630498" /&gt;&lt;/a&gt;&lt;br /&gt;You can &lt;a href="http://sites.google.com/site/lainpsxfiles/a/idctmultiplied.png?attredirects=0"&gt;download&lt;/a&gt; the full 30,000 pixel wide image if you dare.&lt;br /&gt;&lt;br /&gt;All those additions/subtractions help to explain why &lt;a href="http://svn.softwarepublico.gov.br/trac/cacic/browser/cacic/trunk/agente-windows/srcacic/LibJPEG/jidctflt.c?rev=918"&gt;fast IDCT implementations&lt;/a&gt; consist of so many sums and only occasional multiplications.&lt;br /&gt;&lt;br /&gt;The bare math still makes it difficult to identify patterns, so I took things to the extreme and &lt;a href="http://sites.google.com/site/lainpsxfiles/a/idct_visualized.html?attredirects=0&amp;d=1"&gt;visualized it&lt;/a&gt; a bit.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-3210957696854157880?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/3210957696854157880/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2010/03/idct-demystified.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3210957696854157880'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3210957696854157880'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2010/03/idct-demystified.html' title='IDCT Demystified (a little)'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://3.bp.blogspot.com/_vrkdqnCR4Dk/S5tGlBsBbBI/AAAAAAAAALQ/9p5WDxPsFwo/s72-c/idctequation.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-310987365632618229</id><published>2010-02-07T21:52:00.000-08:00</published><updated>2010-04-18T13:01:42.508-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Writing a Java-only Video Player</title><content type='html'>Finally designed and put together a &lt;a href="http://kenai.com/projects/jpsxdec/sources/svn/show/trunk/src/jpsxdec/player?rev=35"&gt;fully working implementation&lt;/a&gt;, involving a custom blocking queue and 6 threads. I&amp;#8217;ve tested it on Windows XP, OS X, and old Kubuntu Hardy. Windows and Mac both look amazing and run perfectly smooth. Unfortunately on Linux the video playback stutters a lot. At first I thought it was due to the GC. After integrating an impressive object pool design, the cause actually turned out to be the Java audio api.&lt;br /&gt;&lt;br /&gt;I use the &lt;a href="http://java.sun.com/javase/6/docs/api/javax/sound/sampled/DataLine.html#getLongFramePosition()"&gt;audio playback position&lt;/a&gt; to determine when a frame should be displayed. Running a little test exposes how reliable this timer is.&lt;br /&gt;&lt;div style="color: #0000aa"&gt;&lt;br /&gt;&lt;div class="content" style="border: 1px solid silver; background: #f4f4f4; padding-left: 0.5em; word-wrap: normal; overflow-x: auto; overflow-y: hidden;"&gt;&lt;!-- Generator: GNU source-highlight 2.11.1&lt;br /&gt;by Lorenzo Bettini&lt;br /&gt;http://www.lorenzobettini.it&lt;br /&gt;http://www.gnu.org/software/src-highlite --&gt;&lt;br /&gt;&lt;pre&gt;&lt;tt&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000080"&gt;import&lt;/span&gt;&lt;/span&gt; javax&lt;span style="color: #990000"&gt;.&lt;/span&gt;sound&lt;span style="color: #990000"&gt;.&lt;/span&gt;sampled&lt;span style="color: #990000"&gt;.*;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;public&lt;/span&gt;&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;class&lt;/span&gt;&lt;/span&gt; &lt;span style="color: #008080"&gt;AudioPositionTest&lt;/span&gt; &lt;span style="color: #FF0000"&gt;{&lt;/span&gt;&lt;br /&gt;    &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;public&lt;/span&gt;&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;static&lt;/span&gt;&lt;/span&gt; &lt;span style="color: #009900"&gt;void&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;main&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;String&lt;span style="color: #990000"&gt;[]&lt;/span&gt; args&lt;span style="color: #990000"&gt;)&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;throws&lt;/span&gt;&lt;/span&gt; LineUnavailableException &lt;span style="color: #FF0000"&gt;{&lt;/span&gt;&lt;br /&gt;        &lt;span style="color: #008080"&gt;AudioFormat&lt;/span&gt; audFmt &lt;span style="color: #990000"&gt;=&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;new&lt;/span&gt;&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;AudioFormat&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;&lt;span style="color: #993399"&gt;18900&lt;/span&gt;&lt;span style="color: #990000"&gt;,&lt;/span&gt; &lt;span style="color: #993399"&gt;16&lt;/span&gt;&lt;span style="color: #990000"&gt;,&lt;/span&gt; &lt;span style="color: #993399"&gt;2&lt;/span&gt;&lt;span style="color: #990000"&gt;,&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;true&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;,&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;true&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;        DataLine&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="color: #008080"&gt;Info&lt;/span&gt; info &lt;span style="color: #990000"&gt;=&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;new&lt;/span&gt;&lt;/span&gt; DataLine&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;Info&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;SourceDataLine&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;class&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;,&lt;/span&gt; audFmt&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;        &lt;span style="color: #008080"&gt;SourceDataLine&lt;/span&gt; player &lt;span style="color: #990000"&gt;=&lt;/span&gt; &lt;span style="color: #990000"&gt;(&lt;/span&gt;SourceDataLine&lt;span style="color: #990000"&gt;)&lt;/span&gt; AudioSystem&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;getLine&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;info&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;        player&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;open&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;audFmt&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;        player&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;start&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;();&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #009900"&gt;byte&lt;/span&gt;&lt;span style="color: #990000"&gt;[]&lt;/span&gt; abBuf &lt;span style="color: #990000"&gt;=&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;new&lt;/span&gt;&lt;/span&gt; &lt;span style="color: #009900"&gt;byte&lt;/span&gt;&lt;span style="color: #990000"&gt;[&lt;/span&gt;&lt;span style="color: #993399"&gt;2&lt;/span&gt; &lt;span style="color: #990000"&gt;*&lt;/span&gt; &lt;span style="color: #993399"&gt;400&lt;/span&gt;&lt;span style="color: #990000"&gt;];&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;        &lt;span style="color: #009900"&gt;long&lt;/span&gt; lngTestLength &lt;span style="color: #990000"&gt;=&lt;/span&gt; &lt;span style="color: #993399"&gt;20&lt;/span&gt; &lt;span style="color: #990000"&gt;*&lt;/span&gt; &lt;span style="color: #993399"&gt;1000&lt;/span&gt;&lt;span style="color: #990000"&gt;;&lt;/span&gt; &lt;span style="font-style: italic"&gt;&lt;span style="color: #9A1900"&gt;// 20 seconds&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;        &lt;span style="color: #009900"&gt;long&lt;/span&gt; lngTestStart &lt;span style="color: #990000"&gt;=&lt;/span&gt; System&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;currentTimeMillis&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;();&lt;/span&gt;&lt;br /&gt;        &lt;span style="color: #009900"&gt;long&lt;/span&gt; lngTestEnd &lt;span style="color: #990000"&gt;=&lt;/span&gt; lngTestStart &lt;span style="color: #990000"&gt;+&lt;/span&gt; lngTestLength&lt;span style="color: #990000"&gt;;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;        System&lt;span style="color: #990000"&gt;.&lt;/span&gt;out&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;println&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;System&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;getProperty&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;&lt;span style="color: #FF0000"&gt;"os.name"&lt;/span&gt;&lt;span style="color: #990000"&gt;)&lt;/span&gt; &lt;span style="color: #990000"&gt;+&lt;/span&gt; &lt;span style="color: #FF0000"&gt;"&lt;/span&gt;&lt;span style="color: #CC33CC"&gt;\t&lt;/span&gt;&lt;span style="color: #FF0000"&gt;Java "&lt;/span&gt; &lt;span style="color: #990000"&gt;+&lt;/span&gt;&lt;br /&gt;                           System&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;getProperty&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;&lt;span style="color: #FF0000"&gt;"java.version"&lt;/span&gt;&lt;span style="color: #990000"&gt;));&lt;/span&gt;&lt;br /&gt;        &lt;span style="color: #008080"&gt;StringBuilder&lt;/span&gt; sb &lt;span style="color: #990000"&gt;=&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;new&lt;/span&gt;&lt;/span&gt; &lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;StringBuilder&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;&lt;span style="color: #993399"&gt;400&lt;/span&gt;&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;        &lt;span style="font-weight: bold"&gt;&lt;span style="color: #0000FF"&gt;while&lt;/span&gt;&lt;/span&gt; &lt;span style="color: #990000"&gt;(&lt;/span&gt;System&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;currentTimeMillis&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;()&lt;/span&gt; &lt;span style="color: #990000"&gt;&amp;lt;&lt;/span&gt; lngTestEnd&lt;span style="color: #990000"&gt;)&lt;/span&gt; &lt;span style="color: #FF0000"&gt;{&lt;/span&gt;&lt;br /&gt;            player&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;write&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;abBuf&lt;span style="color: #990000"&gt;,&lt;/span&gt; &lt;span style="color: #993399"&gt;0&lt;/span&gt;&lt;span style="color: #990000"&gt;,&lt;/span&gt; abBuf&lt;span style="color: #990000"&gt;.&lt;/span&gt;length&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;            &lt;span style="color: #009900"&gt;long&lt;/span&gt; lngTime &lt;span style="color: #990000"&gt;=&lt;/span&gt; System&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;currentTimeMillis&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;();&lt;/span&gt;&lt;br /&gt;            &lt;span style="color: #009900"&gt;long&lt;/span&gt; lngPos &lt;span style="color: #990000"&gt;=&lt;/span&gt; player&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;getLongFramePosition&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;();&lt;/span&gt;&lt;br /&gt;            sb&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;append&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;lngTime &lt;span style="color: #990000"&gt;-&lt;/span&gt; lngTestStart&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;            sb&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;append&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;&lt;span style="color: #FF0000"&gt;'&lt;/span&gt;&lt;span style="color: #CC33CC"&gt;\t&lt;/span&gt;&lt;span style="color: #FF0000"&gt;'&lt;/span&gt;&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;            sb&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;append&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;lngPos&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;            System&lt;span style="color: #990000"&gt;.&lt;/span&gt;out&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;println&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;sb&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;            sb&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;setLength&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;(&lt;/span&gt;&lt;span style="color: #993399"&gt;0&lt;/span&gt;&lt;span style="color: #990000"&gt;);&lt;/span&gt;&lt;br /&gt;            Thread&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;yield&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;();&lt;/span&gt;&lt;br /&gt;        &lt;span style="color: #FF0000"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;        player&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;stop&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;();&lt;/span&gt;&lt;br /&gt;        player&lt;span style="color: #990000"&gt;.&lt;/span&gt;&lt;span style="font-weight: bold"&gt;&lt;span style="color: #000000"&gt;close&lt;/span&gt;&lt;/span&gt;&lt;span style="color: #990000"&gt;();&lt;/span&gt;&lt;br /&gt;    &lt;span style="color: #FF0000"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;span style="color: #FF0000"&gt;}&lt;/span&gt;&lt;/tt&gt;&lt;/pre&gt;&lt;/div&gt;&lt;/div&gt;&lt;br /&gt;Graphing some of the output makes it pretty clear why Linux playback is choppy.&lt;div style="text-align: center"&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/S2-mxaOvtVI/AAAAAAAAAKg/Qya58X1mRCY/s1600-h/20100207-Windows-Playback.gif"&gt;&lt;img style="margin:0 10px 10px 10px;cursor:pointer; cursor:hand;width: 200px; height: 136px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/S2-mxaOvtVI/AAAAAAAAAKg/Qya58X1mRCY/s200/20100207-Windows-Playback.gif" border="0" alt=""id="BLOGGER_PHOTO_ID_5435746643044447570" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/S2-m8AjQkGI/AAAAAAAAAKo/kwx1E2H-eXI/s1600-h/20100207-Kubuntu-Playback.gif"&gt;&lt;img style="margin:0 10px 10px 10px;cursor:pointer; cursor:hand;width: 200px; height: 136px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/S2-m8AjQkGI/AAAAAAAAAKo/kwx1E2H-eXI/s200/20100207-Kubuntu-Playback.gif" border="0" alt=""id="BLOGGER_PHOTO_ID_5435746825129726050" /&gt;&lt;/a&gt;&lt;/div&gt;&lt;br /&gt;Since that isn&amp;#8217;t going to work, my next test will involve registering a &lt;a href="http://java.sun.com/javase/6/docs/api/javax/sound/sampled/Line.html#addLineListener%28javax.sound.sampled.LineListener%29"&gt;listener&lt;/a&gt; for &lt;a href="http://java.sun.com/javase/6/docs/api/javax/sound/sampled/LineEvent.Type.html"&gt;start and stop events&lt;/a&gt;, and track playback time manually. Though I&amp;#8217;m worried my time and the playback time are going to get out of sync.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-310987365632618229?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/310987365632618229/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2010/02/java-media-playback.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/310987365632618229'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/310987365632618229'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2010/02/java-media-playback.html' title='Writing a Java-only Video Player'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_vrkdqnCR4Dk/S2-mxaOvtVI/AAAAAAAAAKg/Qya58X1mRCY/s72-c/20100207-Windows-Playback.gif' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-7450028757512420795</id><published>2009-10-24T09:50:00.001-07:00</published><updated>2010-09-06T15:49:53.290-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Playstation'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>PSX Video Converter Deathmatch</title><content type='html'>&lt;hr&gt;&lt;em&gt;&lt;strong&gt;UPDATE:&lt;/strong&gt; This comparison has been superseeded by a &lt;a href="http://jpsxdec.blogspot.com/2010/09/psx-video-decoders-final-showdown.html"&gt;newer one&lt;/a&gt;&lt;/em&gt;&lt;hr&gt;&lt;br /&gt;I took 8 different video converters and lined them up for the showdown of the decade!&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/SwqstGvFeEI/AAAAAAAAAKY/m7xiYKCSBmk/s1600/G_INFO_STR-all-8-side-by-side.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 400px; height: 356px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/SwqstGvFeEI/AAAAAAAAAKY/m7xiYKCSBmk/s400/G_INFO_STR-all-8-side-by-side.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5407324193513896002" /&gt;&lt;/a&gt;Ok, so it's not really that dramatic. Some points of interest:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;PCSX shows the most amount of blocky artifacts, which is understandable because its converter was designed for speed over quality.&lt;/li&gt;&lt;li&gt;PsxMC, PSmplay, PsxTulz, and PCSX all show very similar coloring. PsxMC and PSmplay are especially similar; however, they are not pixel exact matches.&lt;/li&gt;&lt;li&gt;Q-gears seems to have the darkest and warmest colors of them all, while ffmpeg is the brightest.&lt;/li&gt;&lt;li&gt;jPSXdec seems to produce softer images than the others, and its colors are quite similar to PSXPlay.&lt;/li&gt;&lt;/ul&gt;The differences may not seem very apparent side-by-side, but if you align the images on top of each other (like layers) then toggle the top image's visibility, the differences really stand out.&lt;br /&gt;&lt;br /&gt;Now which is the most accurate? That depends on your definition of accurate.&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Do you want the exact values the PlayStation 1 hardware produces?&lt;/li&gt;&lt;li&gt;Do you want it to match how you see it on the television?&lt;/li&gt;&lt;li&gt;Do you want it to more closely resemble what the original designer created?&lt;/li&gt;&lt;li&gt;Do you want a more mathematically precise conversion?&lt;/li&gt;&lt;/ol&gt;I don't have modded PlayStation hardware, and I don't have any way to very accurately capture composite video output, so I can't investigate #1 or #2. &lt;br /&gt;&lt;br /&gt;You need to have the official Sony PlayStation 1 movie converter tool to investigate #3. If some shifty soul wanted to convert &lt;a href="http://erictheturtlefiles.googlepages.com/ColorBars320x240.avi"&gt;this video&lt;/a&gt; to STR and send it to me, I could investigate further. ;)&lt;br /&gt;&lt;br /&gt;I made my best effort to ensure jPSXdec is very mathematically accurate, so I can at least recommend jPSXdec if you want #4.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://erictheturtlefiles.googlepages.com/psx-video-deathmatch-20091123.zip"&gt;Download all the converted images, along with more details (including some source code)&lt;/a&gt; on how I did all the conversions.&lt;br /&gt;&lt;br /&gt;&lt;i&gt;&lt;b&gt;25Oct2009:&lt;/b&gt; updated download with corrections and included convertible test STR.&lt;/i&gt;&lt;br /&gt;&lt;br /&gt;&lt;i&gt;&lt;b&gt;23Nov2009:&lt;/b&gt; updated download with better PsxTulz screenshot (thanks T_chan!).&lt;/i&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-7450028757512420795?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/7450028757512420795/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2009/10/psx-video-converter-deathmatch.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7450028757512420795'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7450028757512420795'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2009/10/psx-video-converter-deathmatch.html' title='PSX Video Converter Deathmatch'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_vrkdqnCR4Dk/SwqstGvFeEI/AAAAAAAAAKY/m7xiYKCSBmk/s72-c/G_INFO_STR-all-8-side-by-side.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-6974665045216966223</id><published>2009-08-15T04:08:00.001-07:00</published><updated>2009-11-23T23:25:45.113-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>jPSXdec forever</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_vrkdqnCR4Dk/SoaXZstK_nI/AAAAAAAAAJ4/ITocgB-k5Go/s1600-h/locandchurn.png"&gt;&lt;img style="float:right; margin:0 0 10px 10px;cursor:pointer; cursor:hand;width: 200px; height: 125px;" src="http://1.bp.blogspot.com/_vrkdqnCR4Dk/SoaXZstK_nI/AAAAAAAAAJ4/ITocgB-k5Go/s200/locandchurn.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5370146073439043186" /&gt;&lt;/a&gt;&lt;br /&gt;According to Ohloh, jPSXdec is worth at least $150,000, but that is for code from a year ago. It now has now swelled to over 28,000 lines of code in over 170 files, and will probably be past 30k LOC by next version's release.&lt;br /&gt;&lt;br /&gt;I really wish I could work on jPSXdec non-stop until it's ready for prime time again. School, work, the economy, a seriously expensive family emergency, and some critical life changes have all conspired to make that impossible. In fact, I don't have much hope in seeing the next release available anytime this year.&lt;br /&gt;&lt;br /&gt;Things completed so far:&lt;br /&gt;* The complicated part of media playback (managing 6 simultaneous threads isn't easy)&lt;br /&gt;* Much needed cleanup of the Tim decoder, XA ADPCM decoder, and serialization code&lt;br /&gt;* Reorganized the arrangement of media streams verses more static types of media&lt;br /&gt;* Fixed both bugs on the issue list. &lt;br /&gt;* Fixed the Tim false-positive matching that happens fairly often&lt;br /&gt;* Fixed FF7 frame-rate miscalculation&lt;br /&gt;* Break things up by game (i.e. setup plugin system)&lt;br /&gt;* ISO9660 file detection&lt;br /&gt;* Improved detection of audio (including CD-i) and video media items&lt;br /&gt;* More robust disc image detection&lt;br /&gt;&lt;br /&gt;Still to do:&lt;br /&gt;* Re-implement the saving process for the various media types&lt;br /&gt;* Redo frame rate detection&lt;br /&gt;&lt;br /&gt;Beyond the next release:&lt;br /&gt;* Automatic error reporting&lt;br /&gt;* Redo the GUI&lt;br /&gt;* Append AVI writer to make it stricter so it can produce cleaner AVI files&lt;br /&gt;* AVI PNG codec&lt;br /&gt;* Yuv4mpeg2 writing and/or AVI YUV codec&lt;br /&gt;* Real-time media playback/preview&lt;br /&gt;* Searching for static demux and MDEC data&lt;br /&gt;* Finding and uncompressing lhz data, often used in PSX games&lt;br /&gt;* Raw direct CD reading from the disc drive (based on &lt;a href="http://java-avm.sourceforge.net/"&gt;java-avm&lt;/a&gt;)&lt;br /&gt;* CD-i video formats&lt;br /&gt;* More game handling&lt;br /&gt;* STR and XA re-encoders&lt;br /&gt;* CD track audio handling&lt;br /&gt;&lt;br /&gt;When hell freezes over:&lt;br /&gt;A custom hex browser for jPSXdec. Other free and/or open source hex browsers are generally decent, but none do everything I really need. Some desired features:&lt;br /&gt;* Viewing of very large files without loading the whole thing into memory (hundreds of MB) &lt;br /&gt;* Quick viewing and editing values as big/little endian of varying bit sizes/signs/types&lt;br /&gt;More specifically for PSX hacking&lt;br /&gt;* Identifying and browsing by sector (much like CDmage and IsoBuster do)&lt;br /&gt;* Highlighting of the sector headers and footers&lt;br /&gt;* Viewing of continuous demuxed sector payloads&lt;br /&gt;* Identification of known sector types, and the various fields in each&lt;br /&gt;* An overview map of the entire CD, with quick identifying symbols/colors for every sector and its type&lt;br /&gt;The closest thing I've seen to this is VirtualDub's hex viewer. &lt;br /&gt;&lt;br /&gt;And the ultimate pièce de résistance:&lt;br /&gt;* Real-time processing of the data as you mouse-over it, and showing how it results in the final output&lt;br /&gt;* Allows you to take each bit of data in the disc and follow it through the entire decoding process, each step of the way&lt;br /&gt;* Allow you to change anything in real-time, and see how it would turn out&lt;br /&gt;I've repeatedly imagined a program like this for even just mpeg1 or 2 streams. Those streams are really complicated, and you never get to see the direct connection between the data and the output. It would be so neat to hover over a block or a macro block and be able to see exactly where it was going to end up on screen, how it will look, and everything around it. The whole motion detection as well. It would be an incredible tool to teach people how those streams work. In the almost impossible case you've seen the official Bluetooth development tools, that's exactly what I had in mind.&lt;br /&gt;&lt;br /&gt;All these neat ideas could eventually turn jPSXdec into the ultimate PSX hacking utility.&lt;br /&gt;&lt;br /&gt;The time frame for everything? A long...long time. Years probably. Which really makes me wonder: what will become of this project in, say, another decade? Should I start soliciting help?&lt;br /&gt;&lt;br /&gt;In the next to impossible case someone would like to join in developing jPSXdec, his skills might hopefully include:&lt;br /&gt;* Very usable knowledge of Java (no need for an expert because I don't think I am)&lt;br /&gt;* Love and value for clear and well documented source code&lt;br /&gt;* Some experience with reverse-engineering just about anything (media formats preferred)&lt;br /&gt;Added bonus:&lt;br /&gt;* General understanding of mpeg/jpeg-type image formats&lt;br /&gt;* Awareness of cross-platform development issues, and/or experience with developing simple programs for multiple platforms (i.e. Windows, Linux, Mac)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-6974665045216966223?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/6974665045216966223/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2009/08/jpsxdec-forever.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6974665045216966223'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6974665045216966223'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2009/08/jpsxdec-forever.html' title='jPSXdec forever'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_vrkdqnCR4Dk/SoaXZstK_nI/AAAAAAAAAJ4/ITocgB-k5Go/s72-c/locandchurn.png' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-4018820026386911836</id><published>2009-05-08T05:23:00.000-07:00</published><updated>2009-05-20T14:20:01.840-07:00</updated><title type='text'>Comparing Media Quality of Playstation 1 games</title><content type='html'>I suppose &lt;i&gt;very&lt;/i&gt; few people have ever looked as closely at Playstation 1 media as I have. Of those that have, I assume most worked for Sony, or developed games using the official SDK. Of the few that never got that approved proprietary insight, almost all are Japanese. Finally, of those even fewer remaining whose primary language is English, almost none care anymore at this late date. So I thought I'd take a moment and share some of what I've observed.&lt;br /&gt;&lt;br /&gt;To my knowledge, only one game has actually used custom variable-length (i.e. huffman) codes in its video streams: Serial Experiments Lain. The infamous &lt;a href="http://samples.mplayerhq.hu/game-formats/psx-str/"&gt;logo.iki&lt;/a&gt; sample may also use custom huffman codes (it sure doesn't use the standard ones), but until I find what game it's from I can't know for sure.&lt;br /&gt;&lt;br /&gt;Now I assume S.E. Lain's use of custom variable-length codes means its video quality is higher than if the standard set was used, else why would they use it? Its custom decoding software also took full advantage of every last bit of space available to each frame. I've never seen games using the standard SDK decoder that pushed their buffer to the limit. And if that wasn't enough, it sacrificed as much audio quality as it could to increase space for video bandwidth. &lt;br /&gt;&lt;br /&gt;I find this all terribly ironic because the quality of the game's artwork is downright awful. &lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/SgQlBF1zjII/AAAAAAAAAJw/9_pKPM1_nhA/s1600-h/20090508-BadLainAnimation.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 320px; height: 93px;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/SgQlBF1zjII/AAAAAAAAAJw/9_pKPM1_nhA/s320/20090508-BadLainAnimation.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5333428559391460482" /&gt;&lt;/a&gt;So while S.E. Lain's video quality is pointlessly top-notch, its sound quality is not only bad, it is probably one of the worst. The audio was encoded very poorly, with many of the loud moments pointlessly sawed to half the dynamic range, creating excruciating distortions.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_vrkdqnCR4Dk/SgQk2d6T6TI/AAAAAAAAAJo/obvbOGQq3TM/s1600-h/20090412-LainSawWave.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 320px; height: 98px;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/SgQk2d6T6TI/AAAAAAAAAJo/obvbOGQq3TM/s320/20090412-LainSawWave.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5333428376874248498" /&gt;&lt;/a&gt;It's a crying shame, because even though everything about the game was different from the anime series, at least the audio contained more work by the original Lain voice actress, Kaori Shimizu. &lt;br /&gt;&lt;br /&gt;Lain's video decoder also took a small speed hit because the data is stored as big-endian. This means that the little-endian Playstation platform has to take a moment to reverse every 32bit value read from memory. Who knows, maybe reversing it would have sped up the animation of Lain while drudgingly browsing all those media items.&lt;br /&gt;&lt;br /&gt;The game that I've seen with the next best video quality trick is Alice In Cyber Land. It may be the only game that uses variable frame rates. During times with less video action, the frame rate could be dropped, giving the images more bandwidth for detail. When the action picked up again, the frame rate and quality could return to normal so the more rapid frame changes could be shown. I suspect any game's video could be modified to use this feature. In fact, it's really too bad that the official Sony SDK encoder didn't use this trick. So many game videos might have looked even nicer.&lt;br /&gt;&lt;br /&gt;Meanwhile, on the good end of the audio quality spectrum, Square's (now SquareEnix) custom audio format provided the best audio experience of any games I've seen. Its unique format, used in several of their RPGs, produced almost twice the quality of the best standard SDK audio format. An entire sector was devoted to each left/right audio channel, and at intervals that resulted in nearly CD quality output.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-4018820026386911836?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/4018820026386911836/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2009/05/ps1-media-quality-comparison.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/4018820026386911836'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/4018820026386911836'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2009/05/ps1-media-quality-comparison.html' title='Comparing Media Quality of Playstation 1 games'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_vrkdqnCR4Dk/SgQlBF1zjII/AAAAAAAAAJw/9_pKPM1_nhA/s72-c/20090508-BadLainAnimation.png' height='72' width='72'/><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-3524700119402569188</id><published>2009-04-11T04:33:00.000-07:00</published><updated>2010-03-12T20:59:36.856-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><title type='text'>Through the Digital Looking Glass</title><content type='html'>&lt;img style="float:right; margin:0 0 10px 10px;width: 160px; height: 102px;" src="http://1.bp.blogspot.com/_vrkdqnCR4Dk/S5sbcDo_IPI/AAAAAAAAALA/8JM8n6oD01Q/s400/lainlogo.gif" border="0" alt=""id="BLOGGER_PHOTO_ID_5447978343062249714" /&gt;While exhaustively reverse-engineering the Serial Experiments Lain game, always in the back of my mind was an article I read years ago. It describes some curious connections between Lain, and another game called Alice In Cyber Land.&lt;br /&gt;&lt;a href="http://www.cjas.org/~leng/alice.htm"&gt;http://www.cjas.org/~leng/alice.htm&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;So naturally, once the Lain game hacking was thoroughly complete, my attention quickly turned to finding the secrets Alice held. &lt;br /&gt;&lt;br /&gt;The work to discover the unique ways the game stored its videos really paid off. The Alice videos were all well animated, and suggested a game that could be a lot of fun. But for now I must be content with its raw Japanese clips, all of which can now be viewed &lt;a href="http://www.youtube.com/view_play_list?p=AAD2DB9480641831"&gt;on Youtube&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;The Alice In Cyber Land franchise didn't stop with the game. It also included a soundtrack, and &lt;a href="http://www.bcdb.com/cartoon/62318-Alice_In_Cyberland_(Series).html"&gt;short OVA&lt;/a&gt;. It seems at least episode 1 was &lt;a href="http://www.llamas.net/~asudem/fsd/l1_2.html"&gt;fansubbed&lt;/a&gt; by a group called "Boot To Da Head" back in 1997. The first episode is &lt;a href="http://www.youtube.com/view_play_list?p=1C3B6E959F340219"&gt;now watchable&lt;/a&gt; in very low quality, raw Japanese.&lt;br /&gt;&lt;br /&gt;While the connections between Lain and Alice are intriguing, you might be interested to know that they don't end there. Tucked away in a corner of the internet is a little account by one of the game's creators that extends the connections to one more series: Digimon Tamers.&lt;br /&gt;&lt;a href="http://www.konaka.com/alice6/tamers/characters/juri-e.html"&gt;http://www.konaka.com/alice6/tamers/characters/juri-e.html&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-3524700119402569188?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/3524700119402569188/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2009/04/through-digital-looking-glass.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3524700119402569188'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3524700119402569188'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2009/04/through-digital-looking-glass.html' title='Through the Digital Looking Glass'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_vrkdqnCR4Dk/S5sbcDo_IPI/AAAAAAAAALA/8JM8n6oD01Q/s72-c/lainlogo.gif' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-8609422032248699031</id><published>2009-04-06T21:42:00.000-07:00</published><updated>2010-03-12T21:00:09.625-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>CD-i</title><content type='html'>&lt;img style="float:right; margin:0 0 10px 10px;width: 120px; height: 89px;" src="http://4.bp.blogspot.com/_vrkdqnCR4Dk/S5pckgrV8tI/AAAAAAAAAKw/X9cKH3hmDZQ/s400/CDIlogo.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5447768481574810322" /&gt;I was pleasantly surprised when I found someone concocted a clever way of using jPSXdec to &lt;a href="http://cdii.blogspot.com/2009/03/how-to-convert-music-of-cd-i-games-to.html"&gt;decode CD-i audio&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;As explained in &lt;a href="http://jcatki.no-ip.org:8080/cdxa/"&gt;Jonathan Atkins's CDXA documentation&lt;/a&gt;, the Sony Playstation 1 and the Phillips CD-i both used the same audio format on their CDs. It never occurred to me that the CD-i likely has a retro community still following it, much like the Playstation 1 does.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.youtube.com/watch?v=AxdELuxh4f0"&gt;This video&lt;/a&gt; describes a working solution to extracting CD-i audio with jPSXdec that will work with any game. However, after the extraction, you have to manually break up the audio clips and possibly adjust the speed of some.&lt;br /&gt;&lt;br /&gt;Alternatively, you could do the job that jPSXdec can't yet do so the extracted audio clips don't need any extra editing.&lt;br /&gt;&lt;br /&gt;If you let jPSXdec do its best to index the CD (or raw music file), it will find all the audio sectors, but fails to concatenate most of the contiguous streams. You're left with several thousand audio clips with a duration of 1 sector. It wouldn't be too difficult to write a script that checks the audio properties (channel, frequency, etc) and finds what sectors should be combined into a single audio clip. It even sounds like &lt;a href="http://jpsxdec.blogspot.com/2007/11/games-tested.html#c2676625570579519582"&gt;someone has already managed to make some headway with this&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Adding better CD-i audio handling to jPSXdec is quite easy, and will be included in the next release (whenever I can get this redesign finished). As for CD-i video, I can't say I have much motivation (or time) to figure it out. But if anyone wants to get their hands dirty and write some decoding code of their own, I'd be happy to support them however I can.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-8609422032248699031?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/8609422032248699031/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2009/04/cd-i.html#comment-form' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8609422032248699031'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8609422032248699031'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2009/04/cd-i.html' title='CD-i'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_vrkdqnCR4Dk/S5pckgrV8tI/AAAAAAAAAKw/X9cKH3hmDZQ/s72-c/CDIlogo.png' height='72' width='72'/><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-6870771739590870355</id><published>2009-01-27T06:01:00.000-08:00</published><updated>2009-10-08T10:53:47.454-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Translation'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Java real-time video playback</title><content type='html'>Much of the easy changes have already been made to jPSXdec. The biggest and hardest change left is implementing real-time playback. To do this in pure Java is tricky. I've spent a month looking at every kind of Java video player out there.&lt;br /&gt;&lt;br /&gt;I want to keep jPSXdec as cross-platform and simple-to-use as possible (Just Work&amp;trade;). So while the &lt;a href="http://java.sun.com/javase/technologies/desktop/media/jmf/"&gt;JMF&lt;/a&gt; has Java-only implementations for playback, it needs a separate installation, has far more functionality that I need, and being closed source doesn't help. It's curious that even though the JMF has plenty of documented bugs, and hasn't been updated in years, it's still the de facto Java media standard. Meanwhile, the &lt;a href="http://fmj-sf.net/"&gt;FMJ&lt;/a&gt; library is open source, but it's even bigger than JMF, and uses JNI to wield each platform's native playing capabilities. I've examined various other small libraries, but nothing met my needs: a simple synchronized audio and video player. So I'm stuck trying to figure out how to do it myself. &lt;br /&gt;&lt;br /&gt;Initially I thought to duplicate the general design of JMF/FMJ since it seems to work for them. It would also help someone with greater familiarity with those libs to take the next step and properly integrate PSX decoding into them. However, after several days of tearing apart those massive libraries, and seeing I'd only scratched the surface, I dropped that idea. &lt;br /&gt;&lt;br /&gt;Finally went back and took a closer look at &lt;a href="http://sureplayer.sourceforge.net/"&gt;SurePlayer&lt;/a&gt;. It plays mpeg1 movies great with very little processor use. It's fully cross-platform, and is a much more digestible library, so I'll be using that as a guide for implementation. With this clear direction, I can push forward with more jPSXdec development. Maybe in several years when Java 7 is ubiquitous, jPSXdec can be changed to utilize the new &lt;a href="http://weblogs.java.net/blog/chet/archive/2007/05/media_frenzy.html"&gt;JMC&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Also during my searchings I serendipitously ran across a &lt;a href="http://java-avm.sourceforge.net/"&gt;Java library to handle cross-platform raw CD reading&lt;/a&gt;! It's not quite as clean as I would like, but it's a pretty good foundation to build upon.&lt;br /&gt;&lt;br /&gt;In other news, we've had a couple translators pop out of the woodwork recently. Will they be the salvation this project so desperately needs? &lt;br /&gt;&lt;br /&gt;A man can dream.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-6870771739590870355?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/6870771739590870355/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2009/01/java-real-time-video-playback.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6870771739590870355'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6870771739590870355'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2009/01/java-real-time-video-playback.html' title='Java real-time video playback'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-6188002478147628095</id><published>2009-01-04T02:05:00.000-08:00</published><updated>2009-04-11T08:38:31.867-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Translation'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>We're back...sort of</title><content type='html'>We welcome in the new year with &lt;a href="http://psx.lain.pl"&gt;http://psx.lain.pl&lt;/a&gt; coming back online after yet another "I thought it was just temporary" blackout (thanks again go to &lt;tt&gt;toruvinn&lt;/tt&gt; for fixing and hosting the server). Unfortunately the 14% completion still haunts us, and hope for additional progress has not improved. &lt;br /&gt;&lt;br /&gt;As for jPSXdec, I've been making some progress on the redesign, but it will be many months before it will be in shape for another release.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-6188002478147628095?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/6188002478147628095/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2009/01/were-back.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6188002478147628095'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6188002478147628095'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2009/01/were-back.html' title='We&apos;re back...sort of'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-5494690778712179740</id><published>2008-09-24T11:31:00.000-07:00</published><updated>2010-11-04T18:35:01.424-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Playstation'/><title type='text'>How to encode quality PlayStation 1 video</title><content type='html'>&lt;i&gt;Update:&lt;/i&gt; I have since discovered this technique may work, but videos would need to be encoded as mpeg2 due to PlayStation videos having 2 more bits of quality than mpeg1 can handle. Unfortunately that starts getting tricky as mpeg2 has a different chroma subsampling position. In short, this technique has a lot of subtle caveats that should be considered. A future post may be made to explore the issues.&lt;br /&gt;&lt;hr&gt;&lt;p&gt;Recently I've run across a couple of groups trying to replace the video of a PlayStation 1 game. As we have to do the same thing with S.E. Lain, I thought I would share some insight on how it might be done with the highest quality output.&lt;/p&gt;&lt;p&gt;Since there are many things that go into encoding mpeg type images (DCT + quantization being the least of it), that task is best left to programs that know how to do it well, such as ffmpeg. It also allows you to tweak those options, and use its advanced features to get the best results.&lt;/p&gt;&lt;p&gt;So here is how you could do it, broken down into 6 ridiculously complicated steps.&lt;/p&gt;&lt;ol type="1" compact&gt;&lt;li&gt;Convert your video into &lt;a href="http://wiki.multimedia.cx/index.php?title=YUV4MPEG2"&gt;yuv4mpeg2&lt;/a&gt; video (or perhaps an AVI with a YCbCr codec), but using the &lt;a href="http://jpsxdec.blogspot.com/2008/01/psx-yuv-to-yuv4mpeg2.html"&gt;PSX specific rgb-&gt;YCbCr conversion&lt;/a&gt;.&lt;/li&gt;&lt;li&gt;Feed the YCbCr video into ffmpeg at a mpeg1 allowed fps and create a mpeg1 movie with only &lt;a href="http://www.cs.cf.ac.uk/Dave/Multimedia/node248.html"&gt;I-frames&lt;/a&gt; (-intra). This should be done at a variety of different quality levels (-qscale from 1 to n).&lt;/li&gt;&lt;li&gt;Parse the I-frames out of the movie, and parse each frame's macro-blocks&lt;/li&gt;&lt;li&gt;Convert the mpeg1 &lt;a href="http://en.wikipedia.org/wiki/Variable-length_code"&gt;VLC&lt;/a&gt;s to PSX VLCs&lt;/li&gt;&lt;li&gt;Do this for every mpeg1 quality and pick the one that fits best within the amount of space available to each frame&lt;/li&gt;&lt;li&gt;Multiplex the frames and construct all the sectors, including the correct frame headers and the sectors' ECE/EDC codes&lt;/li&gt;&lt;/ol&gt;&lt;p&gt;If the new video is mostly just the old video with some changes (e.g. subtitles) then quality can improved tremendously with this variation.&lt;/p&gt;&lt;ol type="1" start="5" compact&gt;&lt;li&gt;Use some method to determine which macro blocks to replace (manually picking them, or performing a diff on lossless video data, or a fuzzy diff on lossy video data)&lt;/li&gt;&lt;li&gt;Only replace those macro blocks with new ones of the same qscale&lt;/li&gt;&lt;li&gt;If the replaced data makes the frame too big, then either replace the entire frame with an ffmpeg created frame that will fit (qscale will probably be bigger), or remove some quality in the frame to make it smaller&lt;/li&gt;&lt;li&gt;Multiplex the frames and construct all the sectors&lt;/li&gt;&lt;/ol&gt;&lt;p&gt;Alternatively have ffmpeg write an AVI using MJPG codec, then parse the JPEG frames and convert the JPEG VLCs to PSX VLCs (I'm not sure how to get ffmpeg to produce quality variations with the MJPG codec).&lt;/p&gt;&lt;p&gt;Encoding video by the steps above will likely have better results than if you used Sony's official PS1 SDK video encoder (and will also reduce the likelihood of serious legal trouble and C&amp;D letters).&lt;/p&gt;&lt;p&gt;Here is a possible ffmpeg command-line for step 2 above.&lt;/p&gt;&lt;pre&gt;ffmpeg -i source.y4m -vcodec mpeg1video -r 30 -qscale #  \&lt;br /&gt;     -trellis 1 -intra -dc 10 -dct faan -debug dct_coeff \&lt;br /&gt;     -vstats_file qscale#.log out-qscale#.m1v&lt;br /&gt;&lt;br /&gt;-i source.y4m            : yuv4mpeg2 input file&lt;br /&gt;-vcodec mpeg1video       : write mpeg1&lt;br /&gt;-r 30                    : use 30 frames/sec &lt;br /&gt;                           (just to use something &lt;br /&gt;                            compatible with mpeg1)&lt;br /&gt;-qscale #                : chosen qscale&lt;br /&gt;-trellis 1               : trellis quantization&lt;br /&gt;                           does this even apply?&lt;br /&gt;-intra                   : only write I-frames&lt;br /&gt;-dc 10                   : use 10 bits of precision &lt;br /&gt;                           for the DC values? &lt;br /&gt;                           (not sure if this is helpful)&lt;br /&gt;-dct faan                : use a floating-point &lt;br /&gt;                           discrete-cosine-transform &lt;br /&gt;                           for best quality&lt;br /&gt;-debug dct_coeff         : forgot what this does&lt;br /&gt;-vstats_file qscale#.log : write a log of useful info&lt;br /&gt;out-qscale#.m1v          : output file, video only&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-5494690778712179740?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/5494690778712179740/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/09/how-to-encode-quality-playstation-1.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5494690778712179740'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5494690778712179740'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/09/how-to-encode-quality-playstation-1.html' title='How to encode quality PlayStation 1 video'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-6701760600130897397</id><published>2008-07-14T20:18:00.000-07:00</published><updated>2009-04-11T08:39:16.430-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Translation'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>zOMG psx.lain.pl is down!</title><content type='html'>And it has been for quite awhile. I thought it was just temporary, but finally learned yesterday that the good fellow that was nice enough to host the page has chosen to close the account. We are grateful for the time we could use the server. &lt;br /&gt;&lt;br /&gt;Don't worry, we still have all data and work done so far. Unfortunately we're currently without a host, and the project is still stuck at around 14% completion.&lt;br /&gt;&lt;br /&gt;I personally would like to thank everyone that has contributed thus far...&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Hikari&lt;/span&gt; - Translated dialogs from video sequences to Polish.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;phm&lt;/span&gt; - Extracted the media with jpsxdec and setup the wiki. Retranslated video sequences dialogs from Polish to English. Advertised for translators, and coordinated with their changes.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;MercuryTW&lt;/span&gt; - Provided some translations from a translator of his own (Keigo). Edited/corrected translated files.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;stalker-kun&lt;/span&gt; - Provided hosting for the wiki.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;otakufish&lt;/span&gt; - Provided some translations.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;toruvinn&lt;/span&gt; - Provided nice domain.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;farhan&lt;/span&gt; - Ruthlessly proofread random translations, utilising his qualifications in the field of Applied Pedantry with Grammar Nazism.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;fishy&lt;/span&gt; - Proofread translations, created the public project page.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;arc&lt;/span&gt; - Provided some translations.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Jossos&lt;/span&gt; - Provided some translations.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;utakata&lt;/span&gt; - corrected a Japanese transcription.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Najica&lt;/span&gt; - Provided some translations.&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Quibbage&lt;/span&gt; - Created subtitle files for videos.&lt;br /&gt;&lt;br /&gt;...and everyone else (sorry if I've missed your name here)--thank you all very much.&lt;br /&gt;&lt;br /&gt;jPSXdec development has been pretty quiet as well. I should submit the bug that fails to decode some of the Lain videos, or just commit the fix. The next things to do with jPSXdec require some major changes, and things have been busy (my toon won't hit level 60 by itself ;). I'm still here and interested in the project and related topics. I don't plan on that changing anytime soon.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-6701760600130897397?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/6701760600130897397/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/07/zomg-psxlainpl-is-down.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6701760600130897397'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6701760600130897397'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/07/zomg-psxlainpl-is-down.html' title='zOMG psx.lain.pl is down!'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-4741550667183843095</id><published>2008-05-04T17:12:00.000-07:00</published><updated>2009-04-11T08:39:28.240-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Sonic</title><content type='html'>&lt;span style="font-weight:bold;"&gt;AVI&lt;/span&gt;&lt;br /&gt;Fixed the obvious problems with AVI writing, but still problems persist.&lt;br /&gt;* My Windows Quicktime install must be bad because it crashes from like everything (but Mac Quicktime plays fine)&lt;br /&gt;* My Linux mplayer must be bad because it plays all movies stretched, one way or another&lt;br /&gt;* All programs on my lappy crash from my movies except Windows Media Player&lt;br /&gt;* My Linux Totem still plays it with green garbage&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_vrkdqnCR4Dk/SB5RbdMKhVI/AAAAAAAAAGE/qpNIB0UPXNc/s1600-h/TotemGreen.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://4.bp.blogspot.com/_vrkdqnCR4Dk/SB5RbdMKhVI/AAAAAAAAAGE/qpNIB0UPXNc/s320/TotemGreen.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5196680552166098258" /&gt;&lt;/a&gt;So I think I may be doing MJPG slightly wrong, but I'm not sure what. Plus I finally figured out why I could never find any documentation on the MJPG codec: "there is no document that defines a single exact format that is universally recognized as a complete specification of “Motion JPEG” for use in all contexts" &lt;a href="http://en.wikipedia.org/wiki/MJPEG"&gt;Wikipedia&lt;/a&gt; &lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Native decoder&lt;/span&gt;&lt;br /&gt;Got the native decoder working great on Windows, Linux and Mac. CMake has made cross-platform building a breeze :D  It's really exciting to see the decoding plow through dozens of frames per second.&lt;br /&gt;&lt;br /&gt;Indeed, native decoding is fast...&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Java is faster&lt;/span&gt;&lt;br /&gt;The heck?? Contrary to what I thought I saw in my initial tests, my swift Java decoding module is &lt;i&gt;significantly&lt;/i&gt; faster than using the native decoder. How? Not sure, but I suspect it's due to all the overhead needed when calling a JNI function (such as changing big-endian to little-endian). It already melts through 150 sectors/second like a hot knife through butter--but since it spends half its time with garbage collection, could it be faster with some object pooling?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-4741550667183843095?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/4741550667183843095/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/05/sonic.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/4741550667183843095'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/4741550667183843095'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/05/sonic.html' title='Sonic'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_vrkdqnCR4Dk/SB5RbdMKhVI/AAAAAAAAAGE/qpNIB0UPXNc/s72-c/TotemGreen.png' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-6308236540090857868</id><published>2008-04-22T22:12:00.000-07:00</published><updated>2009-04-11T08:39:57.195-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>v0.34</title><content type='html'>I just needed to get something for a public release. It was the re-implementation of the command-line that kept hanging me up (it was boring and I wanted to work on other things ;). I admit in my rush to just get something released, I sorta skimped on the code commenting. :P&lt;br /&gt;&lt;h4&gt;Testing&lt;/h4&gt;Before releasing, I randomly tested jpsxdec on the dozen or so games that my friends let me borrow. As a result I threw in some last-minute changes to handle a couple new movie types. 'Last minute' means these may not even work right (I look forward to finding a way to save variable frame rate movies ^^).&lt;br /&gt;&lt;br /&gt;I ran some quick tests on my Linux Mint machine. Compiz was often rendering the progress window without controls, so there was no way to close the program! And there's an annoying JFileChooser 'All Files' filter bug... :P (just wrote a work-around a moment ago).&lt;br /&gt;&lt;br /&gt;My tests on a Mac were a little more promising. Rendering was slick--even &lt;a href="http://jpsxdec.googlecode.com/svn/trunk/web/macgui.png"&gt;looked better&lt;/a&gt; than Windows rendering.&lt;br /&gt;&lt;br /&gt;After seeing how jpsxdec worked on Linux, I was worried about the quality of jpsxdec--then I saw iTunes for Windows and was feeling pretty good again.&lt;br /&gt;&lt;h4&gt;AVI writing is faulty&lt;/h4&gt;Seems my AVI writer is getting something wrong because it is crashing or otherwise playing poorly on Linux by VLC ('this avi is broken'), mplayer (plays upside-down, stretched, or just crashes), Totem player (green gunk on the screen). On Windows and Mac, Quicktime is having problems (plays video too slowly or crashes). Real Player also crashes the good crash.&lt;br /&gt;&lt;h4&gt;Speed&lt;/h4&gt;Since much of the core decoding work for jpsxdec is finished, I started looking for something a little more exciting to work on. So, following MrVacBob's suggestion, I began writing a crazy fast Java decoder. After doing everything I could think of, and examining the work of &lt;a href="http://peace.snu.ac.kr/dhkim/java/MPEG/"&gt;previous&lt;/a&gt; &lt;a href="http://vsr.informatik.tu-chemnitz.de/~jan/MPEG/MPEG_Play.html"&gt;coders&lt;/a&gt;, I came to the conclusion that a real-time PSX Java decoder may be possible, but the resulting code would be so ugly, long, and annoying, it just isn't worth it. I hope to complete a faster Java decoder that'll cut the decoding time by maybe half, but also make a small, cross-platform native library will be fast enough for real-time playback.&lt;br /&gt;&lt;br /&gt;My friends keep dropping games on me--more than I can keep up with. It takes so long to rip games that I went ahead and threw together raw cd reading on Windows. It's pretty buggy, and I'm sure I'm doing something wrong, but it mostly worked. If ever I can get it more stable, I'll include it. For my Linux coding friends, the JNI Java class is in the source if you feel like writing a Linux version of the lib :)&lt;br /&gt;&lt;h4&gt;Licenses&lt;/h4&gt;The LGPL of the Swing libraries included with jpsxdec don't require that I distribute the source code of the libraries (I haven't changed them, and I am linking them separately). But since jpsxdec is GPL, does that require me to include the LGPL sources with the distribution? I really didn't want the hassle of it, but just to be safe I included the source with the pre-combiled binaries together in the zip files.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-6308236540090857868?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/6308236540090857868/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/04/v034.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6308236540090857868'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6308236540090857868'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/04/v034.html' title='v0.34'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-8620850110730948980</id><published>2008-03-13T19:49:00.000-07:00</published><updated>2009-04-11T08:40:06.147-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Incoming</title><content type='html'>Been wanting to get some stats on jpsxdec code for a long time (Google code doesn't have such features), finally ran across &lt;a href="http://www.statsvn.org/"&gt;StatSVN&lt;/a&gt; and took a quick look at the results.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/R9ntKEnCwiI/AAAAAAAAAF8/MyaR54TovZM/s1600-h/locandchurn.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/R9ntKEnCwiI/AAAAAAAAAF8/MyaR54TovZM/s400/locandchurn.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5177430003931071010" /&gt;&lt;/a&gt;&lt;br /&gt;Now running over 20,000 lines of code, and almost 100 files. Compared to &lt;a href="http://jpsxdec.blogspot.com/2007/10/open-sauce.html"&gt;Oct 21, 2007&lt;/a&gt;'s 7,000 lines, that's 13,000 LOC over 144 days, for a measly 90 lines per day.&lt;br /&gt;&lt;br /&gt;Anyway, I'm guesstimating next week will be the next jpsxdec release. It will have some exciting features:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;&lt;strike&gt;Saving to AVI, both uncompressed and MJPG compressed&lt;/strike&gt; your mileage may vary&lt;/li&gt;&lt;li&gt;&lt;strike&gt;A very nice dialog box providing the many decoding options available&lt;/strike&gt; it's arrite&lt;/li&gt;&lt;li&gt;&lt;strike&gt;Final Fantasy 9 finally working properly&lt;/strike&gt; done!&lt;/li&gt;&lt;li&gt;&lt;strike&gt;Chrono Cross is also working!&lt;/strike&gt; mostly done!&lt;/li&gt;&lt;li&gt;&lt;strike&gt;Cleaned up command-line&lt;/strike&gt; done!&lt;/li&gt;&lt;li&gt;and lots of delicious code documentation :)&lt;/li&gt;&lt;/ul&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-8620850110730948980?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/8620850110730948980/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/03/incoming.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8620850110730948980'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8620850110730948980'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/03/incoming.html' title='Incoming'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_vrkdqnCR4Dk/R9ntKEnCwiI/AAAAAAAAAF8/MyaR54TovZM/s72-c/locandchurn.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-3523088341174357434</id><published>2008-02-25T13:59:00.000-08:00</published><updated>2009-04-11T08:40:19.167-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Translation'/><title type='text'>lain? lain!</title><content type='html'>The &lt;span style="font-weight:bold;"&gt;&lt;a href="http://psx.lain.pl/"&gt;Serial Experiments Lain PSX Game Translation Project&lt;/a&gt;&lt;/span&gt; is really coming along. A few more wonderful translators have generously offered some help. We have roughly 7% of the game translated already.&lt;br /&gt;&lt;br /&gt;Here are some exciting fruits of everyone's efforts so far (actual screenshots).&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://lainpsxfiles.googlepages.com/SLPS_016.04_25022008_134827_0103.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 320px;" src="http://lainpsxfiles.googlepages.com/SLPS_016.04_25022008_134827_0103.png" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://lainpsxfiles.googlepages.com/SLPS_016.04_25022008_134832_0196.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 320px;" src="http://lainpsxfiles.googlepages.com/SLPS_016.04_25022008_134832_0196.png" border="0" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://lainpsxfiles.googlepages.com/serialtranslationlain.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;width: 320px;" src="http://lainpsxfiles.googlepages.com/serialtranslationlain.png" border="0" alt="" /&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-3523088341174357434?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/3523088341174357434/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/02/lain-lain.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3523088341174357434'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3523088341174357434'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/02/lain-lain.html' title='lain? lain!'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-7832516176503124664</id><published>2008-02-17T22:08:00.001-08:00</published><updated>2009-06-16T22:26:58.614-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Translation'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>nihongo niban</title><content type='html'>Much awesomeness has transpired recently. But first, the dull ramblings of jpsxdec status.&lt;br /&gt;&lt;br /&gt;Looked up how to encode uncompressed (RGB) AVI files. It's not too complicated--Microsoft and other sites have usable documentation. Even found a &lt;a href="http://rsb.info.nih.gov/ij/docs/source/ij/plugin/filter/AVI_Writer.java.html"&gt;Java class&lt;/a&gt; to get me started. But I got really excited when the hidden art of MJPG encoding was uncovered. It is so ridiculously easy, I can understand why no one ever describes how to do it.* Of course if we're gonna write AVI files, we need to know the frame-rate. Just a simple 400 lines of code is all that took.* Needed to also change the overall code design to a 'push' architecture with listeners. This had the additional bonus of pulling the actual file writing to the top-level interface--right where it belongs. :D&lt;br /&gt;&lt;br /&gt;* /sarcasm&lt;br /&gt;&lt;br /&gt;But overall things are looking pretty good. For the next release I want to add a new popup window showing the many decoding options. &lt;br /&gt;&lt;br /&gt;Also in the future I want to allow for piping out uncompressed AVI to a program like ffmpeg or mencoder. For Windows I'll also include the infamous Video for Windows. Still need to add raw cd reading. &lt;br /&gt;&lt;br /&gt;But while merrily carrying on with all this, out of nowhere came a fishy fellow with the powers of language transformation! He generously offered to spend some time with the S.E. Lain game. Sooo... efforts on jpsxdec are delayed as the &lt;span style="font-weight:bold;"&gt;Serial Experiments Lain PSX Game Translation Project&lt;/span&gt; commences (SELPGTP?).&lt;br /&gt;&lt;br /&gt;But with 5.5 hours of audio, he has his work cut out for him. Do you share the powers of language transformation? We could really use your help.&lt;br /&gt;&lt;br /&gt;On the technical side, we are working on adding the eventual translation into the game. And I present to you an actual screen shot based on an &lt;a href="http://jpsxdec.blogspot.com/2007/11/nihongo.html"&gt;earlier idea&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_vrkdqnCR4Dk/R7yiRokRfrI/AAAAAAAAAFs/mWGWB_nr_jA/s1600-h/LainModScreenshot200802.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://2.bp.blogspot.com/_vrkdqnCR4Dk/R7yiRokRfrI/AAAAAAAAAFs/mWGWB_nr_jA/s320/LainModScreenshot200802.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5169184896145522354" /&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-7832516176503124664?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/7832516176503124664/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/02/nihongo-niban.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7832516176503124664'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7832516176503124664'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/02/nihongo-niban.html' title='nihongo niban'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_vrkdqnCR4Dk/R7yiRokRfrI/AAAAAAAAAFs/mWGWB_nr_jA/s72-c/LainModScreenshot200802.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-8654165065069143571</id><published>2008-02-02T10:28:00.000-08:00</published><updated>2009-04-11T08:41:43.249-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Amalgamation</title><content type='html'>Been busy with a bunch of different aspects of jpsxdec. Only the GUI and Code Design will be in the next release (v0.31 today!). The rest will show up in releases after that.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;GUI&lt;/span&gt;&lt;br /&gt;Even though it's a pretty lame GUI now, I hope it will drop the bar of entry a little. &lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_vrkdqnCR4Dk/R6TRHUxkAmI/AAAAAAAAAFQ/_YwlDz0Cdp0/s1600-h/gui.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://4.bp.blogspot.com/_vrkdqnCR4Dk/R6TRHUxkAmI/AAAAAAAAAFQ/_YwlDz0Cdp0/s200/gui.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5162480996639310434" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Code Design&lt;/span&gt;&lt;br /&gt;I had difficulty deciding on highest-level interface between the GUI/CLI and the logic. So I set it aside and worked on other things.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;PSX YUV-&amp;gt;yuv4mpeg2 conversion matrix&lt;/span&gt;&lt;br /&gt;This will allow jpsxdec to output more accurate .yuv image sequences.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Frame Rate Calculation&lt;/span&gt;&lt;br /&gt;I thought it was a good idea to guess the exact FF7 frame rate algorithm via trial-and-error. 8 hours later I finally saw that FF7 frame lengths do actually follow a pattern, but a ridiculous one. I hoped it would come to a frame rate of exactly 15/100.1% (half the rate of NTSC). That is close, but there was no way I could guess the underlying algorithm of this...&lt;br /&gt;&lt;br /&gt;&lt;script type="text/javascript"&gt;tag = "blk20080202"; s = "if (document.getElementById('"+tag+"').style.display == 'block') " + "document.getElementById('"+tag+"').style.display = 'none'; " + "else document.getElementById('"+tag+"').style.display = 'block'; "; document.write('&lt;a name ="'+tag+'" href="#'+tag+'" onclick="'+s+'"&gt;Show/hide code&lt;/a&gt;'); document.write('&lt;div id="'+tag+'" style="display:none"&gt;'); &lt;/script&gt; &lt;pre&gt;&lt;br /&gt;    if (iMovieType == WACKED_NTSC1 &amp;amp;&amp;amp; iThisFrame == 101)&lt;br /&gt;        iThisFrameLength = 11;&lt;br /&gt;    if (iMovieType == WACKED_NTSC2 &amp;amp;&amp;amp; iThisFrame == 100)&lt;br /&gt;        iThisFrameLength = 11;&lt;br /&gt;    else if (iThisFrame == 200)&lt;br /&gt;        iThisFrameLength = 11;&lt;br /&gt;    else if (iThisFrame &amp;gt;= 203 &amp;amp;&amp;amp; iThisFrame &amp;lt;= 298) {&lt;br /&gt;        if (((iThisFrame - 203) % 4) == 0)&lt;br /&gt;            iThisFrameLength = 11;&lt;br /&gt;        else if (((iThisFrame - 203) % 4) == 1)&lt;br /&gt;            iThisFrameLength = 9;&lt;br /&gt;        else&lt;br /&gt;            iThisFrameLength = 10;&lt;br /&gt;    }&lt;br /&gt;    else if (iThisFrame == 299)&lt;br /&gt;        iThisFrameLength = 11;&lt;br /&gt;    else if (iThisFrame &amp;gt;= 303 &amp;amp;&amp;amp; iThisFrame &amp;lt;= 398) {&lt;br /&gt;        if (((iThisFrame - 303) % 4) == 0)&lt;br /&gt;            iThisFrameLength = 11;&lt;br /&gt;        else if (((iThisFrame - 303) % 4) == 1)&lt;br /&gt;            iThisFrameLength = 9;&lt;br /&gt;        else&lt;br /&gt;            iThisFrameLength = 10;&lt;br /&gt;    } &lt;br /&gt;    else if (iThisFrame == 399)&lt;br /&gt;        iThisFrameLength = 11;&lt;br /&gt;    else if (iThisFrame &amp;gt;= 402 &amp;amp;&amp;amp; iThisFrame &amp;lt; 497) {&lt;br /&gt;        if (((iThisFrame - 402) % 4) == 0)&lt;br /&gt;            iThisFrameLength = 11;&lt;br /&gt;        else if (((iThisFrame - 402) % 4) == 2)&lt;br /&gt;            iThisFrameLength = 9;&lt;br /&gt;        else&lt;br /&gt;            iThisFrameLength = 10;&lt;br /&gt;    }&lt;br /&gt;    else if (iThisFrame == 498)&lt;br /&gt;        iThisFrameLength = 11;&lt;br /&gt;    else if (iThisFrame == 501)&lt;br /&gt;        iThisFrameLength = 11;&lt;br /&gt;    else if (iThisFrame &amp;gt;= 504 &amp;amp;&amp;amp; iThisFrame &amp;lt;= 600) {&lt;br /&gt;        if (((iThisFrame - 504) % 4) == 0)&lt;br /&gt;            iThisFrameLength = 9;&lt;br /&gt;        else if (((iThisFrame - 504) % 4) == 2)&lt;br /&gt;            iThisFrameLength = 11;&lt;br /&gt;        else&lt;br /&gt;            iThisFrameLength = 10;&lt;br /&gt;    } &lt;br /&gt;    else&lt;br /&gt;        iThisFrameLength = 10;&lt;br /&gt;&lt;/pre&gt;&lt;script type="text/javascript"&gt;document.write('&lt;/div&gt;'); &lt;/script&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Raw CD reading (Windows)&lt;/span&gt;&lt;br /&gt;Made a native program to read raw CD sectors via DeviceIoControl. It's a simple interactive prompt that accepts commands to open/close a CD and read sectors.  I even setup a Java program to communicate with the native program via stdin/out. Unfortunately it was slow, and was very vulnerable to deadlock while reading from stdin. I also started adding ASPI for raw CD reading, but there seems to be a lot more to using that API.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Encoding via VFW (Video for Windows)&lt;/span&gt;&lt;br /&gt;I worked out a little program to convert a series of raw image and audio data into an AVI, using the oh-so-familiar Video for Windows popup. I wonder if it can handle accepting all the audio at once, then all the video at once....&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_vrkdqnCR4Dk/R6TRMExkAnI/AAAAAAAAAFY/BW_Va30Xzqc/s1600-h/vfw.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://3.bp.blogspot.com/_vrkdqnCR4Dk/R6TRMExkAnI/AAAAAAAAAFY/BW_Va30Xzqc/s200/vfw.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5162481078243689074" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;JNI&lt;/span&gt;&lt;br /&gt;Even though I said it would be a &lt;a href="http://jpsxdec.blogspot.com/2007/10/goals-and-roadmap.html"&gt;pain in the butt&lt;/a&gt;, I guess it's really not so bad. It's kinda like translating VB6 COM code into C++. This will likely speed up raw CD reading, and save me from communicating via stdin/out.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Code Design&lt;/span&gt;&lt;br /&gt;Finally got back to this again. Since no solution was particularly attractive, I went with the simplest one. This will only use one optional &lt;strike&gt;callback&lt;/strike&gt; listener (for progress status). &lt;br /&gt;&lt;br /&gt;However, I have begun to think that the 'pull' architecture is not the best approach to begin with. A 'push' architecture is more applicable to this situation: as sectors are read from the disc, they need to be 'pushed' into the appropriate streams. Listeners can be added to collect the streams of interest. If jpsxdec was to ever play media in real time (not likely), this would be the necessary design. In any case, the 'push' approach would make decoding a little faster because there is less seek time.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-8654165065069143571?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/8654165065069143571/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/02/amalgamation.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8654165065069143571'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8654165065069143571'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/02/amalgamation.html' title='Amalgamation'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_vrkdqnCR4Dk/R6TRHUxkAmI/AAAAAAAAAFQ/_YwlDz0Cdp0/s72-c/gui.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-1309908718594960736</id><published>2008-01-20T19:47:00.000-08:00</published><updated>2010-07-12T13:56:09.285-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Playstation'/><title type='text'>PSX YCbCr to yuv4mpeg2</title><content type='html'>&lt;h4&gt;PSX YCbCr&lt;/h4&gt;Given Y, Cb, and Cr color range of [-128, 127].&lt;pre&gt;                              PSX&lt;br /&gt;[ 1   0        1.402  ]   [ Y + 128 ]    [ r ]&lt;br /&gt;[ 1  -0.3437  -0.7143 ] * [ Cb      ] =  [ g ]&lt;br /&gt;[ 1   1.772    0      ]   [ Cr      ]    [ b ]&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;h4&gt;yuv4mpeg2 (i.e. Rec.601) YCbCr&lt;/h4&gt;Given Y color range of [16, 235] and Cb,Cr color range of [16, 240].&lt;pre&gt;                              Rec.601&lt;br /&gt;[ 1.164   0       1.59  ]   [ Y  - 16  ]     [ r ]&lt;br /&gt;[ 1.164  -0.391  -0.813 ] * [ Cb - 128 ]  =  [ g ]&lt;br /&gt;[ 1.164   2.018   0     ]   [ Cr - 128 ]     [ b ]&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;To convert a PSX YCbCr color to a Rec.601 YCbCr color:&lt;br /&gt;&lt;pre&gt;&lt;br /&gt;&lt;strike&gt;[ 1  -3415973/13224846875  1242172/13224846875 ]&lt;br /&gt;[ 0   105814197/105798775      -5608/105798775 ]&lt;br /&gt;[ 0       19492/105798775  105791687/105798775 ]&lt;/strike&gt;&lt;br /&gt;&lt;br /&gt;&lt;strike&gt;Answer:  yuv4mpeg2^-1 * PSX =&lt;br /&gt;[ 1  3415973/13225888625  -1242172/13225888625 ]&lt;br /&gt;[ 0  105791687/105807109        5608/105807109 ]&lt;br /&gt;[ 0     -19492/105807109   105814197/105807109 ]&lt;/strike&gt;&lt;br /&gt;&lt;br /&gt;Rec601_YCbCr = &lt;br /&gt;                                     PSX&lt;br /&gt;                                     [Y + 128]   [ 16]&lt;br /&gt;     Rec601_Matrix^-1 * PSX_Matrix * [Cb     ] + [128]&lt;br /&gt;                                     [Cr     ]   [128]&lt;br /&gt;&lt;/pre&gt;Where&lt;pre&gt;Rec601_Matrix^-1 * PSX_Matrix =&lt;br /&gt;&lt;br /&gt;     [250/291 -488509/2660418030 -82738/1330209015]&lt;br /&gt;     [0          4014411/4571165       164/4571165]&lt;br /&gt;     [0            3673/27426990   8031459/9142330]&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;Thanks to &lt;tt&gt;toruvinn&lt;/tt&gt; for refreshing me on matrix math, and &lt;a href="http://www.calc101.com/webMathematica/matrix-algebra.jsp"&gt;this site&lt;/a&gt; and &lt;a href="http://maxima.sourceforge.net/"&gt;Maxima&lt;/a&gt; for saving me from lots of raw calculations.&lt;br /&gt;&lt;br /&gt;&lt;i&gt;Update 27Feb2010: Fixed.&lt;/i&gt;&lt;br /&gt;&lt;i&gt;Update 23Mar2010: Really fixed.&lt;/i&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-1309908718594960736?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/1309908718594960736/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/01/psx-yuv-to-yuv4mpeg2.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/1309908718594960736'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/1309908718594960736'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/01/psx-yuv-to-yuv4mpeg2.html' title='PSX YCbCr to yuv4mpeg2'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-7991075029562294073</id><published>2008-01-06T12:00:00.000-08:00</published><updated>2009-04-11T08:42:21.762-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>HATSUHINODE</title><content type='html'>&lt;img style="float:left; margin:0 10px 10px 0;" src="http://1.bp.blogspot.com/_vrkdqnCR4Dk/R4E_x1zKugI/AAAAAAAAAFI/EcQkdIvxkRg/s320/BONENKAI.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5152469574176389634" /&gt;Hope all had a pleasant new year. As we enter 2008, it is interesting to note that this year marks the 10th anniversary of the Serial Experiments Lain anime series, along with the Playstation game.&lt;br /&gt;&lt;br /&gt;Now that holidays are over, I finally managed to release the latest compiled executable on the &lt;a href="http://code.google.com/p/jpsxdec/downloads/list"&gt;download page&lt;/a&gt;. No changes to the program interface (same wonderful command-line that you're used to ;), but it has all the latest internal goodness that I hope actually works--most notable is it now &lt;span style="font-style:italic;"&gt;[edit] &lt;/span&gt;&lt;span style="font-weight:bold;"&gt;mostly&lt;/span&gt; supports FF8 &lt;span style="font-style:italic;"&gt;(it would help to fully test it before making such calims :P)&lt;/span&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-7991075029562294073?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/7991075029562294073/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2008/01/hatsuhinode.html#comment-form' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7991075029562294073'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/7991075029562294073'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2008/01/hatsuhinode.html' title='HATSUHINODE'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_vrkdqnCR4Dk/R4E_x1zKugI/AAAAAAAAAFI/EcQkdIvxkRg/s72-c/BONENKAI.jpg' height='72' width='72'/><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-3936590997977887914</id><published>2007-12-14T13:12:00.000-08:00</published><updated>2009-04-11T08:44:50.446-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Happy Winter Solstice</title><content type='html'>This time of year brings, among other things, demands that defy the known laws of time and space. So further updates for jPSXdec and the STR file format will have to wait until after the holidays. &lt;br /&gt;&lt;br /&gt;In the works:&lt;ul&gt;&lt;li&gt;&lt;strike&gt;Full FF8 support&lt;/strike&gt; done!&lt;/li&gt;&lt;li&gt;&lt;strike&gt;GUI&lt;/strike&gt; well, it's something&lt;/li&gt;&lt;li&gt;&lt;strike&gt;Removing dependence on Java 1.6, down to 1.5&lt;/strike&gt; done!&lt;/li&gt;&lt;li&gt;&lt;strike&gt;FF9 video support&lt;/strike&gt; video yes, audio no&lt;/li&gt;&lt;li&gt;&lt;strike&gt;TIM image searching and converting&lt;/strike&gt; need to include more comprehensive TIM searching&lt;/li&gt;&lt;/ul&gt;So until then, may you have a pleasant season, and take a moment to ponder upon whatever higher power you may believe in (*cough*lain*cough*).&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_vrkdqnCR4Dk/R2LyQ4XoDzI/AAAAAAAAAFA/Ywtvhw7qT08/s1600-h/loveisover.jpg"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://4.bp.blogspot.com/_vrkdqnCR4Dk/R2LyQ4XoDzI/AAAAAAAAAFA/Ywtvhw7qT08/s320/loveisover.jpg" border="0" alt=""id="BLOGGER_PHOTO_ID_5143940096233836338" /&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-3936590997977887914?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/3936590997977887914/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/12/happy-winter-solstice.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3936590997977887914'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/3936590997977887914'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/12/happy-winter-solstice.html' title='Happy Winter Solstice'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_vrkdqnCR4Dk/R2LyQ4XoDzI/AAAAAAAAAFA/Ywtvhw7qT08/s72-c/loveisover.jpg' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-5587502629414080773</id><published>2007-11-29T08:15:00.000-08:00</published><updated>2011-05-19T23:32:13.723-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Games tested with jPSXdec</title><content type='html'>&lt;u&gt;PLEASE LEAVE A COMMENT ABOUT ANY GAME YOU USED WITH JPSXDEC&lt;/u&gt;&lt;br /&gt;&lt;br /&gt;Alundra 2 - works&lt;br /&gt;Valkyrie Profile - works&lt;br /&gt;Xenogears - works&lt;br /&gt;Final Fantasy Chronicles - works (video at 30 fps)&lt;br /&gt;Saiyuki: Journey West - works&lt;br /&gt;Intelligent Qube - works&lt;br /&gt;Power Puff Girls - works&lt;br /&gt;Simpsons Wrestling - works&lt;br /&gt;Super Puzzle Fighter 2 Turbo - works&lt;br /&gt;Lethal Enforcers 1 and 2 - works&lt;br /&gt;Battle Arena Toshinden - works&lt;br /&gt;Metal Gear Solid - works&lt;br /&gt;Silent Hill - works&lt;br /&gt;Tekken 3 - works&lt;br /&gt;Xeno Gears - works&lt;br /&gt;Motorhead - works&lt;br /&gt;Oddworld Abes Oddysee - works&lt;br /&gt;Spyro - works&lt;br /&gt;Worms World Party - works&lt;br /&gt;Soul Blade - works&lt;br /&gt;R4 Ridge Racer Type 4 - works&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;font-style:italic;"&gt;Samples from &lt;a href="http://samples.mplayerhq.hu/game-formats/psx-str/"&gt;ffmpeg examples&lt;/a&gt;&lt;/span&gt;&lt;br /&gt;abc000.str - works (video at 30 fps)&lt;br /&gt;descent_descent-e.str.bz2 - works&lt;br /&gt;finalfantasyVII_movie-gold4.mov.bz2 - works&lt;br /&gt;jumpingflash2_music2.xai.bz2 - works&lt;br /&gt;jumpingflash2_movie-01.str.bz2 - works&lt;br /&gt;lain.str - works&lt;br /&gt;lunar2.str - works (video just under 20 fps)&lt;br /&gt;river1.str - works (video at 12.5 fps)&lt;br /&gt;st3.xa - works&lt;br /&gt;logo.iki - works (from game "UmJammer Lammy")&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;font-style:italic;"&gt;Games requiring special handling&lt;/span&gt;&lt;br /&gt;Serial Experiments Lain - works&lt;br /&gt;FF7 - works&lt;br /&gt;FF8 - works&lt;br /&gt;FF9 - works&lt;br /&gt;Chrono Cross - works&lt;br /&gt;Alice in Cyberland - works&lt;br /&gt;Sonic Wings Special - last movie seems like filler data, but can be converted if it is first copied off the disc normally&lt;br /&gt;Ace Combat 3 - works&lt;br /&gt;Legend of Mana&lt;br /&gt;&lt;br /&gt;Gran Turismo?&lt;br /&gt;G-Generation?&lt;br /&gt;Ko'hloons Gate?&lt;br /&gt;Maborosi (まぼろし月夜) Moonlit Night?&lt;br /&gt;Formula 1?&lt;br /&gt;Lunar 2?&lt;br /&gt;BeatMania 4?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-5587502629414080773?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/5587502629414080773/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/games-tested.html#comment-form' title='15 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5587502629414080773'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5587502629414080773'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/games-tested.html' title='Games tested with jPSXdec'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>15</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-2318809600269190130</id><published>2007-11-09T20:05:00.000-08:00</published><updated>2009-04-11T08:45:25.934-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><title type='text'>"Huve Fun With Family Movie"</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_vrkdqnCR4Dk/RzUuKR-oJKI/AAAAAAAAAE4/Cy7KQ5qNsiI/s1600-h/huve_fun.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://1.bp.blogspot.com/_vrkdqnCR4Dk/RzUuKR-oJKI/AAAAAAAAAE4/Cy7KQ5qNsiI/s320/huve_fun.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5131058104618198178" /&gt;&lt;/a&gt;&lt;br /&gt;...with out warranty of any kid.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-2318809600269190130?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/2318809600269190130/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/huve-fun.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/2318809600269190130'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/2318809600269190130'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/huve-fun.html' title='&quot;Huve Fun With Family Movie&quot;'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_vrkdqnCR4Dk/RzUuKR-oJKI/AAAAAAAAAE4/Cy7KQ5qNsiI/s72-c/huve_fun.png' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-9116881822923040755</id><published>2007-11-06T08:02:00.000-08:00</published><updated>2009-04-11T08:46:21.176-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><title type='text'>#lain</title><content type='html'>Through a lucky course of events, the folks over at a Lain IRC channel ran across my page. As &lt;span style="font-family: monospace;"&gt;farhan&lt;/span&gt; put it, &lt;span style="font-family: monospace;"&gt;"i suppose lain favours your blog"&lt;/span&gt;. The people were friendly, and I met an excellent tester that helped with the jPSXdec development (thanks phm!). &lt;br /&gt;&lt;br /&gt;If you love Lain, and know how to get around IRC (or can fake it, like I do ;), then feel free to join us at IRCnet (open.ircnet.net or maybe irc.ircnet.com) &lt;span style="font-family: monospace;"&gt;#lain&lt;/span&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-9116881822923040755?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/9116881822923040755/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/lain.html#comment-form' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/9116881822923040755'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/9116881822923040755'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/lain.html' title='&lt;span style=&quot;font-family: monospace;&quot;&gt;#lain&lt;/span&gt;'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-8022184482943890703</id><published>2007-11-04T20:52:00.000-08:00</published><updated>2009-04-11T08:46:55.589-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><title type='text'>nihongo</title><content type='html'>Since I began the task of decoding the Serial Experiments Lain Playstation movies years ago, I've hoped some friendly multi-lingual folks might someday translate all the audio and movies into English. I've always assumed the translated media would be downloadable, separate from the game itself, until I met a fellow who had the lofty desire to put the translated media back into the game.&lt;br /&gt;&lt;br /&gt;I wondered what he was going to do about the 2 hours of audio. Dubbing seems the only option. But while finally playing through the whole game the other night, I found there are many sound-effects and characters in the audio portions. I would hate to lose all that to dubbing (not to mention my preference for sub-titles). &lt;br /&gt;&lt;br /&gt;However, I also noticed the pictures shown in the background as you listen to audio, and I started thinking...&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_vrkdqnCR4Dk/Ry6x0Ya2Y3I/AAAAAAAAAEY/OwFWFXFEuJI/s1600-h/Translation.png"&gt;&lt;img style="display:block; margin:0px auto 10px; text-align:center;cursor:pointer; cursor:hand;" src="http://4.bp.blogspot.com/_vrkdqnCR4Dk/Ry6x0Ya2Y3I/AAAAAAAAAEY/OwFWFXFEuJI/s320/Translation.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5129232539087954802" /&gt;&lt;/a&gt;&lt;br /&gt;Not an actual screen-shot (you can tell by the pixels), but I have the ability to make it so. This isn't a perfect solution, but could be an alternative to dubbing (and it's probably easier too).&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-8022184482943890703?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/8022184482943890703/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/nihongo.html#comment-form' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8022184482943890703'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8022184482943890703'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/11/nihongo.html' title='nihongo'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_vrkdqnCR4Dk/Ry6x0Ya2Y3I/AAAAAAAAAEY/OwFWFXFEuJI/s72-c/Translation.png' height='72' width='72'/><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-8401679095668432857</id><published>2007-10-27T16:36:00.000-07:00</published><updated>2009-04-11T08:48:07.485-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Close the world, Open the nExt.</title><content type='html'>After watching and enjoying the Serial Experiments Lain anime series, my interest was piqued by something I saw on the disc extras.&lt;br /&gt;&lt;br /&gt;A Lain Playstation game.&lt;br /&gt;&lt;br /&gt;And I had to own it.&lt;br /&gt;&lt;br /&gt;With the help of my Japanese co-worker during my trip to Japan, I managed to acquire a copy all of my own.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.geocities.com/punistation10/"&gt;Jen's site&lt;/a&gt; was accurate when it said there was very little info about the game. Following her lead, I wanted to change that. I wanted to decode the video for all to see. The audio could be ripped just fine, but the video refused to decode. Endless Googles later and I was still left wanting.&lt;br /&gt;&lt;br /&gt;While toying with the game in an emulator, it dawned on me that if I couldn't decode the video off the disc, maybe I could let the game do it for me. I got the &lt;i&gt;open source&lt;/i&gt; &lt;a href="http://sourceforge.net/projects/peops/"&gt;P.E.Op.S. GPU&lt;/a&gt; plug-in and went to work grabbing the video frames before anything was drawn over them. Soon I had nearly all the media from disc 1 sitting on my hard drive.&lt;br /&gt;&lt;br /&gt;However, I ran into a snag. The decoded audio from the disc wasn't lining up with the video frames I had captured.&lt;br /&gt;&lt;br /&gt;I had big plans, but was burning out and couldn't ever find a reason for this discrepancy. The project was abandoned for another day.&lt;br /&gt;&lt;br /&gt;Two years later...&lt;br /&gt; &lt;br /&gt;Finding myself still stumped over the audio/video mismatching, I veered a different direction. Could I possibly learn how to decode PSX videos myself? &lt;br /&gt;&lt;br /&gt;Another endless bout of Googles later and I learned about JPEG and MPEG encoding. Soon I had my own I-frame decoder. It was the &lt;a href="http://q-gears.sourceforge.net/"&gt;Q-gears&lt;/a&gt; &lt;a href="http://q-gears.svn.sourceforge.net/viewvc/q-gears/branches/old_sources/src/common/movie/decoders/"&gt;source code&lt;/a&gt; that finally pushed the decoder into aligning with PSX data. It was done. I was seeing video frames from games I'd &lt;a href="http://samples.mplayerhq.hu/game-formats/psx-str/"&gt;never seen before&lt;/a&gt;, and without ever touching someone else's decoder.&lt;br /&gt;&lt;br /&gt;I could do what existing decoders could do, but what of Lain? What is with all this video data? It doesn't add up to anything sensible. Again I hit a snag. The only way to know what the data means is to see what the game is doing, and how could I do that?&lt;br /&gt;&lt;br /&gt;I was just about ready to settle with my mis-matched audio and video frames, but I couldn't leave well enough alone. I ran across the &lt;a href="http://psxemulator.gazaxian.com/"&gt;pSX emulator&lt;/a&gt; that provides debugging capabilities. So over a three day weekend I swam through a sea of R3051 assembly code. By the end I knew &lt;a href="http://jpsxdec.blogspot.com/2007/10/teh-h4x0rz.html"&gt;how it is all done&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Outraged at the lack of information and source code about the PSX, I decided to take my little decoder to the big time and share everything I have learned over the last few months. &lt;br /&gt;&lt;br /&gt;And thus is the &lt;a href="http://code.google.com/p/jpsxdec/"&gt;jPSXdec&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-8401679095668432857?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/8401679095668432857/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/close-world-open-next.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8401679095668432857'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/8401679095668432857'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/close-world-open-next.html' title='Close the world, Open the nExt.'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-5438975326579664469</id><published>2007-10-21T03:13:00.000-07:00</published><updated>2009-04-11T08:49:44.887-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Open Sauce</title><content type='html'>As mentioned in the project goals, the code will be open source. And I want to make sure this source code stays open and free (unlike so many hacking tools before this one). As such, I plan on releasing jPSXdec under &lt;strike&gt;GPL v3&lt;/strike&gt; &lt;a href="http://www.gnu.org/licenses/gpl-2.0.html"&gt;GPL v2&lt;/a&gt; (for better compatibility). &lt;br /&gt;&lt;br /&gt;Initially, I thought simply providing the source compressed in an archive on this site would be sufficient. I've mentioned a &lt;a href="http://jpsxdec.blogspot.com/2007/10/goals-and-roadmap.html"&gt;few ways&lt;/a&gt; people could help with the development if they were interested. I kept these very modular, so incorporating them would be fairly easy. I also didn't think the source code would be very large. &lt;br /&gt;&lt;br /&gt;But there has been a request to setup a &lt;a href="http://en.wikipedia.org/wiki/Comparison_of_free_software_hosting_facilities"&gt;code repository&lt;/a&gt; instead. I've also realized the size of the source code is already non-trivial (almost 7000 lines of code), and will only grow larger (especially if a GUI is added).&lt;br /&gt;&lt;br /&gt;I'm all for setting up a code repository, however, I don't know anything about existing hosting sites (except &lt;a href="http://sourceforge.net/"&gt;SF&lt;/a&gt;), nor do I have any experience setting up or maintaining such a site. I wish I could list some criteria, but I'm not even sure what I'll need. If anyone has any thoughts/info/suggestions/insight, I'd be interested in hearing them.&lt;blockquote&gt;&lt;span style="font-weight:bold;"&gt;Update:&lt;/span&gt; After carefully weighing the different options, I found that &lt;a href="http://code.google.com/p/jpsxdec/"&gt;Google Code&lt;/a&gt; was the best choice after all (thanks phm).&lt;/blockquote&gt;&lt;br /&gt;I will also be releasing two tidbits of documentation:&lt;ul&gt;&lt;li&gt;documentation about the code, describing how the different classes are organized and used.&lt;/li&gt;&lt;li&gt;a lengthy text file describing the STR file format and decoding process (nearly complete).&lt;/li&gt;&lt;/ul&gt;While I'm somewhat familiar with the GPL license, I've never had any experience with licensing documentation. It seems there are two recommended options: GNU FDL and FreeBSD Documentation License. After reading a little about them, I'm not sure which to choose. Again, if anyone has any thoughts, please share.&lt;blockquote&gt;&lt;span style="font-weight:bold;"&gt;Update:&lt;/span&gt; Went with MIT license.&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;Thanks!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-5438975326579664469?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/5438975326579664469/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/open-sauce.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5438975326579664469'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5438975326579664469'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/open-sauce.html' title='Open Sauce'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-2277356576343374606</id><published>2007-10-18T11:14:00.001-07:00</published><updated>2009-04-11T08:50:08.083-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Playstation'/><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Links</title><content type='html'>Numerous links were followed during the development of this program. All of these were valid at the time I followed them. I'm just throwing these in here for now. I'll clean it up later.&lt;br /&gt;&lt;br /&gt;PSX Tools&lt;br /&gt;http://hitmen.c02.at/html/psx_tools.html&lt;br /&gt;http://members.fortunecity.com/zlasher/files/toolz.html&lt;br /&gt;http://www.psxforum.com/utilities.php&lt;br /&gt;http://www.geocities.com/anapan8/cv/&lt;br /&gt;&lt;br /&gt;Decoding links&lt;br /&gt;http://jcatki.no-ip.org/cdxa/&lt;br /&gt;http://www.momentaryfascinations.com/technology/the.spyro.soundtracks.html&lt;br /&gt;http://forums.qhimm.com/index.php?topic=6473.0&lt;br /&gt;http://forums.qhimm.com/index.php?topic=6140.0&lt;br /&gt;http://q-gears.svn.sourceforge.net/viewvc/q-gears/trunk/src/common/movie/decoders/&lt;br /&gt;http://wiki.multimedia.cx/index.php?title=PlayStation_Motion_Decoder&lt;br /&gt;http://osdir.com/ml/video.xine.devel/2003-02/msg00179.html&lt;br /&gt;http://osdir.com/ml/video.xine.devel/2003-02/msg00186.html&lt;br /&gt;http://samples.mplayerhq.hu/game-formats/psx-str/&lt;br /&gt;http://www.koders.com/c/fidF23C1EAFCEAF84CA539927A01093D37D9695722A.aspx&lt;br /&gt;&lt;!-- http://www.assemblergames.com/forums/showthread.php?t=10148 &lt;br /&gt;http://eatsushi.org/content/console/psx_tools/dox/PDG.doc&lt;br /&gt;--&gt;&lt;br /&gt;MPEG1 links&lt;br /&gt;http://bmrc.berkeley.edu/research/mpeg/faq/mpeggeneral.html &lt;!-- &lt;br /&gt;http://www.ee.eng.chula.ac.th/~supava/doc/mpeg12.pdf --&gt;&lt;br /&gt;http://www.chiariglione.org/ride/inside_MPEG-1/inside_MPEG-1.htm&lt;br /&gt;http://www.andrewduncan.ws/MPEG/MPEG-1_Picts.html&lt;br /&gt;http://www.geocities.com/xhelmboyx/quicktime/formats/mpeg-layout.txt&lt;br /&gt;http://www.faqs.org/faqs/mpeg-faq/&lt;br /&gt;http://www.wotsit.org/list.asp?search=mpeg&lt;br /&gt;http://guru.multimedia.cx/the-mpeg124-and-h26123-idct/&lt;br /&gt;http://www.uow.edu.au/~nabg/MPEG/IDCT.html&lt;br /&gt;&lt;br /&gt;Other Info&lt;br /&gt;http://forum.digital-digest.com/showthread.php?t=17898&lt;br /&gt;http://www.greenspun.com/bboard/q-and-a-fetch-msg.tcl?msg_id=000tS4&lt;br /&gt;http://groups.google.com/group/alt.games.sony-playstation/browse_thread/thread/3bb9cc7ce10bbb58/02098464ed19f81a?hl=ened19f81a&lt;br /&gt;http://www.megagames.com/psx/psx_copy_patch_linux.shtml&lt;br /&gt;http://rpgd.emulationworld.com/klarth/&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-2277356576343374606?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/2277356576343374606/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/links.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/2277356576343374606'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/2277356576343374606'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/links.html' title='Links'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-6641740129391026253</id><published>2007-10-16T20:41:00.000-07:00</published><updated>2009-04-11T08:52:03.364-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jPSXdec'/><title type='text'>Goals and Roadmap</title><content type='html'>I have some simple goals for this project.&lt;ul&gt;&lt;li&gt;Cross-platform&lt;/li&gt;&lt;li&gt;Open source&lt;/li&gt;&lt;li&gt;Very well documented&lt;/li&gt;&lt;li&gt;Very clear, direct, non-obfuscated, and well documented source code (specifically the video decoding portion)&lt;/li&gt;&lt;li&gt;More stable than existing decoders&lt;/li&gt;&lt;li&gt;Capable of decoding all types of audio and video that existing decoders can, plus more&lt;/li&gt;&lt;li&gt;Highest decoding quality possible&lt;/li&gt;&lt;/ul&gt;The program is written in Java because it helps meet many of these goals.&lt;br /&gt;&lt;br /&gt;Unfortunately, the goals to make the source code as clear as possible, and highest decoding quality, have the side effect of making the decoder rather slow. Right now it decodes between 0.5-4 frames per second on my 2.8Ghz machine. The only way I plan on improving the speed is by using a disgustingly obfuscated IDCT. Since that is by far the slowest part of the decoder, it could help a lot. &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;The first version will simply be a command-line tool. It will decode video into a series of images, and the audio into a wav file. It will handle standard STR files, plus a few special formats: Final Fantasy VII, &lt;strike&gt;Final Fantasy VIII&lt;/strike&gt; (delayed to 2nd version), and Serial Experiments Lain. &lt;br /&gt;&lt;br /&gt;The next version I plan to include raw CD reading (for Windows), fix bugs, and maybe add some more special game handling. I think I also want to add raw file copying off CDs.&lt;br /&gt;&lt;br /&gt;Following that, I hope to add a GUI to the program. I'm thinking of duplicating much of PsxMC's interface.&lt;br /&gt;&lt;br /&gt;I'm not sure what to do about encoding the movies into another movie format. Trying to use Video for Windows in Java would be a pain in the butt (read JNI), and it also wouldn't be cross platform. My current thought is to do what &lt;a href="http://jmencode.sourceforge.net/"&gt;jMencode&lt;/a&gt; does: provide a GUI for open-source encoding programs. It appears mencoder can encode using the computer's Video for Windows codecs. But I know how much everyone likes, and is familiar with how Video for Windows works. So currently I don't have a clear plan of what to do.&lt;br /&gt;&lt;br /&gt;Want to help? Come up with a GUI, an encoding method, or raw CD reading for Linux/Mac!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-6641740129391026253?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/6641740129391026253/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/goals-and-roadmap.html#comment-form' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6641740129391026253'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/6641740129391026253'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/goals-and-roadmap.html' title='Goals and Roadmap'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-3811573850891467526.post-5968085276113213812</id><published>2007-10-14T11:53:00.001-07:00</published><updated>2009-04-11T08:50:20.921-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Lain'/><title type='text'>teh h4x0rz</title><content type='html'>&lt;pre&gt;0xyyuu0038rrrr0000&lt;br /&gt;yy = Luminance quantization scale&lt;br /&gt;uu = Chrominance quantization scale&lt;br /&gt;rrrr = number of run length codes in frame&lt;br /&gt;&lt;br /&gt;v3 DC Coefficients style&lt;br /&gt;11s                     (0, 1)&lt;br /&gt;011s                    (0, 2)&lt;br /&gt;0100 s                  (1, 1)&lt;br /&gt;0101 s                  (0, 3)&lt;br /&gt;0010 1s                 (0, 4)&lt;br /&gt;0011 0s                 (2, 1)&lt;br /&gt;0011 1s                 (0, 5)&lt;br /&gt;0001 00s                (0, 6)&lt;br /&gt;0001 01s                (3, 1)&lt;br /&gt;0001 10s                (1, 2)&lt;br /&gt;0001 11s                (0, 7)&lt;br /&gt;0000 100s               (0, 8)&lt;br /&gt;0000 101s               (4, 1)&lt;br /&gt;0000 110s               (0, 9)&lt;br /&gt;0000 111s               (5, 1)&lt;br /&gt;0010 0000 s             (0, 10)&lt;br /&gt;0010 0001 s             (0, 11)&lt;br /&gt;0010 0010 s             (1, 3)&lt;br /&gt;0010 0011 s             (6, 1)&lt;br /&gt;0010 0100 s             (0, 12)&lt;br /&gt;0010 0101 s             (0, 13)&lt;br /&gt;0010 0110 s             (7, 1)&lt;br /&gt;0010 0111 s             (0, 14)&lt;br /&gt;0000 0010 00s           (0, 15)&lt;br /&gt;0000 0010 01s           (2, 2)&lt;br /&gt;0000 0010 10s           (8, 1)&lt;br /&gt;0000 0010 11s           (1, 4)&lt;br /&gt;0000 0011 00s           (0, 16)&lt;br /&gt;0000 0011 01s           (0, 17)&lt;br /&gt;0000 0011 10s           (9, 1)&lt;br /&gt;0000 0011 11s           (0, 18)&lt;br /&gt;0000 0001 0000 s        (0, 19)&lt;br /&gt;0000 0001 0001 s        (1, 5)&lt;br /&gt;0000 0001 0010 s        (0, 20)&lt;br /&gt;0000 0001 0011 s        (10, 1)&lt;br /&gt;0000 0001 0100 s        (0, 21)&lt;br /&gt;0000 0001 0101 s        (3, 2)&lt;br /&gt;0000 0001 0110 s        (12, 1)&lt;br /&gt;0000 0001 0111 s        (0, 23)&lt;br /&gt;0000 0001 1000 s        (0, 22)&lt;br /&gt;0000 0001 1001 s        (11, 1)&lt;br /&gt;0000 0001 1010 s        (0, 24)&lt;br /&gt;0000 0001 1011 s        (0, 28)&lt;br /&gt;0000 0001 1100 s        (0, 25)&lt;br /&gt;0000 0001 1101 s        (1, 6)&lt;br /&gt;0000 0001 1110 s        (2, 3)&lt;br /&gt;0000 0001 1111 s        (0, 27)&lt;br /&gt;0000 0000 1000 0s       (0, 26)&lt;br /&gt;0000 0000 1000 1s       (13, 1)&lt;br /&gt;0000 0000 1001 0s       (0, 29)&lt;br /&gt;0000 0000 1001 1s       (1, 7)&lt;br /&gt;0000 0000 1010 0s       (4, 2)&lt;br /&gt;0000 0000 1010 1s       (0, 31)&lt;br /&gt;0000 0000 1011 0s       (0, 30)&lt;br /&gt;0000 0000 1011 1s       (14, 1)&lt;br /&gt;0000 0000 1100 0s       (0, 32)&lt;br /&gt;0000 0000 1100 1s       (0, 33)&lt;br /&gt;0000 0000 1101 0s       (1, 8)&lt;br /&gt;0000 0000 1101 1s       (0, 35)&lt;br /&gt;0000 0000 1110 0s       (0, 34)&lt;br /&gt;0000 0000 1110 1s       (5, 2)&lt;br /&gt;0000 0000 1111 0s       (0, 36)&lt;br /&gt;0000 0000 1111 1s       (0, 37)&lt;br /&gt;0000 0000 0100 00s      (2, 4)&lt;br /&gt;0000 0000 0100 01s      (1, 9)&lt;br /&gt;0000 0000 0100 10s      (1, 24)&lt;br /&gt;0000 0000 0100 11s      (0, 38)&lt;br /&gt;0000 0000 0101 00s      (15, 1)&lt;br /&gt;0000 0000 0101 01s      (0, 39)&lt;br /&gt;0000 0000 0101 10s      (3, 3)&lt;br /&gt;0000 0000 0101 11s      (7, 3)&lt;br /&gt;0000 0000 0110 00s      (0, 40)&lt;br /&gt;0000 0000 0110 01s      (0, 41)&lt;br /&gt;0000 0000 0110 10s      (0, 42)&lt;br /&gt;0000 0000 0110 11s      (0, 43)&lt;br /&gt;0000 0000 0111 00s      (1, 10)&lt;br /&gt;0000 0000 0111 01s      (0, 44)&lt;br /&gt;0000 0000 0111 10s      (6, 2)&lt;br /&gt;0000 0000 0111 11s      (0, 45)&lt;br /&gt;0000 0000 0010 000s     (0, 47)&lt;br /&gt;0000 0000 0010 001s     (0, 46)&lt;br /&gt;0000 0000 0010 010s     (16, 1)&lt;br /&gt;0000 0000 0010 011s     (2, 5)&lt;br /&gt;0000 0000 0010 100s     (0, 48)&lt;br /&gt;0000 0000 0010 101s     (1, 11)&lt;br /&gt;0000 0000 0010 110s     (0, 49)&lt;br /&gt;0000 0000 0010 111s     (0, 51)&lt;br /&gt;0000 0000 0011 000s     (0, 50)&lt;br /&gt;0000 0000 0011 001s     (7, 2)&lt;br /&gt;0000 0000 0011 010s     (0, 52)&lt;br /&gt;0000 0000 0011 011s     (4, 3)&lt;br /&gt;0000 0000 0011 100s     (0, 53)&lt;br /&gt;0000 0000 0011 101s     (17, 1)&lt;br /&gt;0000 0000 0011 110s     (1, 12)&lt;br /&gt;0000 0000 0011 111s     (0, 55)&lt;br /&gt;0000 0000 0001 0000 s   (0, 54)&lt;br /&gt;0000 0000 0001 0001 s   (0, 56)&lt;br /&gt;0000 0000 0001 0010 s   (0, 57)&lt;br /&gt;0000 0000 0001 0011 s   (21, 1)&lt;br /&gt;0000 0000 0001 0100 s   (0, 58)&lt;br /&gt;0000 0000 0001 0101 s   (3, 4)&lt;br /&gt;0000 0000 0001 0110 s   (1, 13)&lt;br /&gt;0000 0000 0001 0111 s   (23, 1)&lt;br /&gt;0000 0000 0001 1000 s   (8, 2)&lt;br /&gt;0000 0000 0001 1001 s   (0, 59)&lt;br /&gt;0000 0000 0001 1010 s   (2, 6)&lt;br /&gt;0000 0000 0001 1011 s   (19, 1)&lt;br /&gt;0000 0000 0001 1100 s   (0, 60)&lt;br /&gt;0000 0000 0001 1101 s   (9, 2)&lt;br /&gt;0000 0000 0001 1110 s   (24, 1)&lt;br /&gt;0000 0000 0001 1111 s   (18, 1)&lt;br /&gt;0000 01                 MPEG1 escape style&lt;br /&gt;10                      EOB&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/3811573850891467526-5968085276113213812?l=jpsxdec.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jpsxdec.blogspot.com/feeds/5968085276113213812/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/teh-h4x0rz.html#comment-form' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5968085276113213812'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/3811573850891467526/posts/default/5968085276113213812'/><link rel='alternate' type='text/html' href='http://jpsxdec.blogspot.com/2007/10/teh-h4x0rz.html' title='teh h4x0rz'/><author><name>m35</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry></feed>
