GOPchop - MPEG2 GOP-accurate editor
Released under GNU General Public License
Kees Cook (kees@outflux.net)


This tool is used for people wanting to take sections out of MPEG2-PS 
files without re-encoding the resulting frames.  The idea is to write 
specific "Group of Pictures" (GOP) sections to a new MPEG2-PS file.  These 
GOPs will decode correctly (in theory), and the gaps won't be noticed.  I 
wrote this tool to edit commercials out of MPEG2 files produced by my 
capture card.  Using this tool for anything else is really beyond the 
scope of its design.


Requirements
------------
For GOPchop to work, you need two things: GTK-1.2, and the CVS version of
mpeg2dec. For mpeg2dec, it's expected that all the libraries and includes
have been installed on your system.  One particular library (libvo)
didn't appear to install during "make install".  This library can be found
in mpeg2dec-0.2.1-cvs/libvo/, if your CVS version doesn't already have this
fixed.  Copy it to where ever the other mpeg2dec libraries went, and
"configure" should notice it.  Or you can aim "--with-libs=" to where you
compiled mpeg2dec.


Configuring/Compiling
---------------------
"./configure" should do the trick.  If you have RedHat or some pre-3.0 
gcc, you may have Issues(tm) compiling (and running).  I'd recommend using
3.0+ of gcc and g++.  If you have both packages installed (RedHat 7.2), you
can run "CC=gcc3 CXX=g++3 ./configure" to force configure to use the right
compiler.

I'm still inexperienced when it comes to making and using "./configure" 
files, so for computers that are not mine, you might have to fix things to 
get everything to compile.  If you find stuff that needs correcting, 
please email me and I'll update it.  :)

This is the command line I used to run configure:
CC=gcc3 CXX=gcc3 ./configure --with-libs=/video/mpeg2/mpeg2dec-0.2.1-cvs/libvo

And finally:
make
make install

If things blow up with autoconf or automake, try doing "cd src" before doing
the "make" and "make install".  I'm not very good with configure scripts, and
this stuff was all generated for me by Glade.

If things still resist working right, please email me, and hopefully we can
figure it out.  :)


Using GOPchop
-------------
The basic way to use GOPchop is like so:

 1) Run GOPchop.
 2) Select an MPEG2 with "File / Open".
 3) Drag the slider to the first GOP you want to have in a clip.
		(You can disable "Options / Auto-Refresh" to seek
		 faster, and then click "Refresh" to see where you
		 are in the file.)
 4) Click "Start Mark".
 5) Drag the slider to the last GOP you want in the clip.
 6) Click "End Mark".  (If you drag the slider somewhere before the
		first mark, "End Mark" will not do anything.)
 7) Repeat steps 3 through 6 to select all the clips you want saved.
 8) Drag clips up and down to reorder them in the Clip List window.
 9) To delete unwanted clips, select it, and hit Del or Backspace.
10) Save the clips to a new MPEG2 with "File / Save Clips".

If you want to save different clips, select "File / Clear Clips" and start 
over at step 3.  If you want to use a different source MPEG2, select "File 
/ Close" and start over at step 1.

At present, I don't support saving clips from multiple different MPEG2 
source files.  In the future, perhaps.

This is a *LOSSY* process on MPEGs that have open GOPs.  To close a GOP, I
must toss B-Frames at the start of a GOP.  If you were to mark each frame in
an MPEG for splicing in GOPchop, you would end up with fewer frames than you
started with.  To "close" an open GOP, I must toss those B-Frames.


VOB Files
---------
Since DVD VOB files are MPEG2, you can use GOPchop to pull scenes.  
HOWEVER, GOPchop is not a DVD-authentication tool.  I might go look at 
libdvdread, but I require an mmap-able file interface (like, say, a direct 
filesystem "open" call).  If you have unencrypted DVDs, or can get the 
unencrypted VOB somewhere to use "open" on it, GOPchop should have no 
problems with it.


What to expect during MPEG2 loading
-----------------------------------
Please keep an eye on your standard error output.  If you have a file that
GOPchop doesn't like, you'll hear about it during load on stderr.

Usually, when GOPchop loads an MPEG2, there will be some "errors" near the 
end of the file.  These errors can generally be ignored.  They have to do 
with how your MPEG2 was created, and expected packet information or 
end-of-file codes might be missing.  That's perfectly okay.  (Even MPEG2s 
_made_ by GOPchop issue this warning.  :P)

I didn't implement parsing for every MPEG2 System packet header out there.  
It's in my TODO list to do it, but you might not be able to load some 
MPEG2s.  The error will say something about "Need to write a parsing 
routine".  Email me if you run into this, and I can get it finished up for 
you.

If you have an MPEG2-PS file that doesn't have GOPs correctly built, you may
need to remultiplex your MPEG2-PS file first.  I recommend using "mplex" from
the siemens DVB tools: http://www.linuxtv.org/download/dvb/

If your MPEG2-PS file doesn't map single Packs to each Frame, GOPchop may
also get freaky.


How it works
------------
I scan the MPEG2 for a full list of System packets, then examine the
Program Element Stream packets they contain.  In the video PES, I look for
GOP headers (and Picture headers).  Each GOP is then mapped back to the
System packets that contain it (a full GOP can span multiple VES packets,
and multiple System packets).  When a GOP is saved to a new file, the
entire System packet list for that GOP is written as a byte-for-byte copy
from the source MPEG2. In theory, this will take any audio streams along
for the ride.  So far, so good.  :)

In the "Info" box, the "Offset" column shows the system packet offset
(for GOPs) and the video packet offset (for Pictures).  The "Bytes"
column lists the bytes contained by all the system packets (for the GOP),
and all the video packets in a Picture.  You'll notice that the Offset
plus the Bytes don't add up to the next Picture's Offset.  This is because
there is stuff between the video packets.  :)  The GOP "Bytes" and "Offset",
however, should add up to the next GOP's "Offset" value.


KNOWN ISSUES
------------
mpeg2dec (and libvo) sometimes just up and segfault when they bring up a
window.  I think this is from a bad compiler (using gcc 3+ seems to have
made the problem go away for me.)  I hope you don't see this bug, but it
doesn't appear to be my code's fault.  ;)

Some audio streams don't take kindly to be chopped like this.  However, 
they usually have CRC to detect problems.  For example, when I snipped
together some scenes from a DVD, and when played it back with "MPlayer",
the AC3 audio stream reported CRC errors and gracefully dropped the garbled 
packet.  As for the playback, I didn't notice it at all.

GOPchop assumes that all GOPs will appear in the first video PES packet of 
a System packet.  Technically, this might not be true, but in practice, 
this seems to happen.  As a result, GOPchop could fail to load some 
"unusual" MPEG2 files.  If you have some examples, please email me, and 
maybe I can fix my code.  :)

Since GOPchop doesn't alter the stream it writes back to disk, things like
time-stamps are really bizarre.  In players like MPlayer, you'll see the
time-stamp during playing jump forward at each splice point.  In fact,
this seriously breaks some players, and I'm hoping to figure out how to
get around it.

The "correct" way to edit is to just set the "broken" flag in the GOP, and
the decoder will throw away the B-frames following the I-frame in an open
GOP.  However, it seems that at least mpeg2dec doesn't honor the "broken"
flag, and I bet other decoders don't too.  Therefore, I've done BOTH: I've
set the "broken" flag, AND removed the B-Frames.  I'm worried that this will
break time sync, but it's the only way to stop from having decoding artifacts
due to the B-frames in the open GOP referring to some previous P-Frame that
doesn't exist any more.



Acknowledgements
----------------
Kirsten for not kicking me out of the house while I hacked the first version
of this together for a week straight.  :)

Paul for having lots and lots of commercials to edit out of KFir huge MPEG2s.

Various people from the KFir MPEG2 list (mpeg2@linuxtv.org) for guiding me
towards this program's basic design and helping to stomp bugs, especially:
	Warren Young (warren@etr-usa.com)
	Marcus Metzler (mocm@convergence.de)
	Bram Stolk (b.stolk@chello.nl)

Brian (briand@zipcon.net) for being so patient with my broken builds.  :)

My fantastic "beta testers" who didn't know they were getting into beta
testing until it was too late:
	Chris Chiappa <chris@chiappa.net>		(TiVo Extraction)
	Stuart L. Morris <stuart@xover.co.uk>		(TS-to-PS)
	Wolfgang Goeller <wgoeller@swissonline.ch>




-- 
Kees Cook (kees@outflux.net)
http://outflux.net/
