| 1 |
pcg |
1.1 |
#!/usr/bin/perl |
| 2 |
|
|
|
| 3 |
|
|
use Video::Capture::V4l; |
| 4 |
|
|
use Video::RTjpeg; |
| 5 |
|
|
|
| 6 |
|
|
$|=1; |
| 7 |
|
|
$SIG{PIPE} = 'IGNORE'; |
| 8 |
|
|
|
| 9 |
|
|
$stream = "/tmp/vstream"; |
| 10 |
|
|
require $stream; |
| 11 |
|
|
|
| 12 |
|
|
$mpegencode = "/root/cvt/mpeg_movie-1.6.0/video_in/mpeg_encode"; |
| 13 |
|
|
|
| 14 |
|
|
my $gop = 8; |
| 15 |
|
|
|
| 16 |
|
|
$tmpdir = "/tmp/encode$$/"; |
| 17 |
|
|
$tmpdir = "/tmp/encode"; |
| 18 |
|
|
mkdir $tmpdir, 0700; |
| 19 |
|
|
|
| 20 |
|
|
$fsize = $w*$h*2; |
| 21 |
|
|
|
| 22 |
|
|
$partlen = $fps*60; |
| 23 |
|
|
$partlen = $gop*100; |
| 24 |
|
|
|
| 25 |
|
|
my @dec; |
| 26 |
|
|
|
| 27 |
|
|
sub new_vdecoder { |
| 28 |
|
|
my $number = @dec; |
| 29 |
|
|
my $decp = do { local *DECODER_READER }; |
| 30 |
|
|
my $decc = do { local *DECODER_WRITER }; |
| 31 |
|
|
pipe $decp, $decc; |
| 32 |
|
|
if (fork==0) { |
| 33 |
|
|
my ($buf, $tables); |
| 34 |
|
|
open DATA, "<$outprefix.v$number" or die; |
| 35 |
|
|
|
| 36 |
|
|
read DATA, $buf, 4; |
| 37 |
|
|
my ($tlen) = unpack "N*", $buf; |
| 38 |
|
|
|
| 39 |
|
|
read DATA, $tables, $tlen; |
| 40 |
|
|
Video::RTjpeg::init_decompress($tables, $w, $h); |
| 41 |
|
|
|
| 42 |
|
|
while (read DATA, $buf, 8) { |
| 43 |
|
|
my ($time, $size) = unpack "N*", $buf; |
| 44 |
|
|
print $decc pack "N", $time; |
| 45 |
|
|
read DATA, $buf, $size; |
| 46 |
|
|
print $decc Video::RTjpeg::decompress $buf; |
| 47 |
|
|
} |
| 48 |
|
|
exit; |
| 49 |
|
|
} |
| 50 |
|
|
push @dec, $decp; |
| 51 |
|
|
} |
| 52 |
|
|
|
| 53 |
|
|
my @nframeid; |
| 54 |
|
|
|
| 55 |
|
|
sub next_frame { |
| 56 |
|
|
my $min = 1e30; |
| 57 |
|
|
my $buf; |
| 58 |
|
|
my $minid; |
| 59 |
|
|
for (0..$#dec) { |
| 60 |
|
|
unless (defined $nframeid[$_]) { |
| 61 |
|
|
read $dec[$_], $buf, 4; |
| 62 |
|
|
$nframeid[$_] = unpack "N", $buf; |
| 63 |
|
|
} |
| 64 |
|
|
($min,$minid) = ($nframeid[$_],$_) if $nframeid[$_] < $min && defined $nframeid[$_]; |
| 65 |
|
|
} |
| 66 |
|
|
read $dec[$minid], $buf, $fsize; |
| 67 |
|
|
undef $nframeid[$minid]; |
| 68 |
|
|
($buf, $min); |
| 69 |
|
|
} |
| 70 |
|
|
|
| 71 |
|
|
new_vdecoder for 1..$vencoders; |
| 72 |
|
|
|
| 73 |
|
|
my $part = 0; |
| 74 |
|
|
|
| 75 |
|
|
sub do_encode { |
| 76 |
|
|
my ($pstart, $pframes) = @_; |
| 77 |
|
|
$pframes = sprintf "%06d", $pframes-1; |
| 78 |
|
|
$part = sprintf "%03d", $part+1; |
| 79 |
|
|
|
| 80 |
|
|
open TEMPLATE, ">$tmpdir/param" or die; |
| 81 |
|
|
print TEMPLATE <<EOF; |
| 82 |
|
|
OUTPUT $outprefix.$part.mpg |
| 83 |
|
|
|
| 84 |
|
|
#PATTERN IBBBPBBB |
| 85 |
|
|
PATTERN IBBBPBBBPBBBPBBBPBBBPBBBPBBBPBBB |
| 86 |
|
|
FORCE_ENCODE_LAST_FRAME |
| 87 |
|
|
|
| 88 |
|
|
# You must specify the type of the input files. The choices are: |
| 89 |
|
|
# YUV, PPM, JMOVIE, Y, JPEG, PNM |
| 90 |
|
|
# |
| 91 |
|
|
BASE_FILE_FORMAT YUV |
| 92 |
|
|
|
| 93 |
|
|
# this option is ignored if BASE_FILE_FORMAT is not YUV and you're running |
| 94 |
|
|
YUV_SIZE ${w}x$h |
| 95 |
|
|
|
| 96 |
|
|
# EYUV or UCB are the same as previous versions of this encoder. |
| 97 |
|
|
# (All the Y's, then U's then V's, in 4:2:0 subsampling.) |
| 98 |
|
|
# Other formats, such as Abekas, Phillips, or a general format are |
| 99 |
|
|
# permissible, the general format is a string of Y's, U's, and V's |
| 100 |
|
|
# to specify the file order. |
| 101 |
|
|
|
| 102 |
|
|
INPUT_FORMAT EYUV |
| 103 |
|
|
|
| 104 |
|
|
INPUT_CONVERT * |
| 105 |
|
|
|
| 106 |
|
|
# number of frames in a GOP. |
| 107 |
|
|
# |
| 108 |
|
|
# since each GOP must have at least one I-frame, the encoder will find the |
| 109 |
|
|
# the first I-frame after GOP_SIZE frames to start the next GOP |
| 110 |
|
|
# |
| 111 |
|
|
# later, will add more flexible GOP signalling |
| 112 |
|
|
# |
| 113 |
|
|
GOP_SIZE $partlen |
| 114 |
|
|
|
| 115 |
|
|
# number of slices in a frame |
| 116 |
|
|
# |
| 117 |
|
|
# 1 is a good number. another possibility is the number of macroblock rows |
| 118 |
|
|
# (which is the height divided by 16) |
| 119 |
|
|
# |
| 120 |
|
|
SLICES_PER_FRAME $w |
| 121 |
|
|
|
| 122 |
|
|
# directory to get all input files from (makes this file easier to read) |
| 123 |
|
|
INPUT_DIR $tmpdir |
| 124 |
|
|
|
| 125 |
|
|
# There are a bunch of ways to specify the input files. |
| 126 |
|
|
# from a simple one-per-line listing, to the following |
| 127 |
|
|
# way of numbering them. See the manual for more information. |
| 128 |
|
|
INPUT |
| 129 |
|
|
# '*' is replaced by the numbers 01, 02, 03, 04 |
| 130 |
|
|
# if I instead do [01-11], it would be 01, 02, ..., 09, 10, 11 |
| 131 |
|
|
# if I instead do [1-11], it would be 1, 2, 3, ..., 9, 10, 11 |
| 132 |
|
|
# if I instead do [1-11+3], it would be 1, 4, 7, 10 |
| 133 |
|
|
# the program assumes none of your input files has a name ending in ']' |
| 134 |
|
|
# if you do, too bad!!! |
| 135 |
|
|
# |
| 136 |
|
|
# |
| 137 |
|
|
frame*.yuv [000000-$pframes] |
| 138 |
|
|
END_INPUT |
| 139 |
|
|
|
| 140 |
|
|
# Many of the remaining options have to do with the motion search and qscale |
| 141 |
|
|
|
| 142 |
|
|
# FULL or HALF -- must be upper case |
| 143 |
|
|
PIXEL HALF |
| 144 |
|
|
|
| 145 |
|
|
# means +/- this many pixels for both P and B frame searches |
| 146 |
|
|
# specify two numbers if you wish to serc different ranges in the two. |
| 147 |
|
|
RANGE 10 |
| 148 |
|
|
|
| 149 |
|
|
# this must be one of {EXHAUSTIVE, SUBSAMPLE, LOGARITHMIC} |
| 150 |
|
|
PSEARCH_ALG LOGARITHMIC |
| 151 |
|
|
|
| 152 |
|
|
# this must be one of {SIMPLE, CROSS2, EXHAUSTIVE} |
| 153 |
|
|
# |
| 154 |
|
|
# note that EXHAUSTIVE is really, really, really slow |
| 155 |
|
|
# |
| 156 |
|
|
BSEARCH_ALG CROSS2 |
| 157 |
|
|
|
| 158 |
|
|
# |
| 159 |
|
|
# these specify the q-scale for I, P, and B frames |
| 160 |
|
|
# (values must be between 1 and 31) |
| 161 |
|
|
# These are the Qscale values for the entire frame in variable bit-rate |
| 162 |
|
|
# mode, and starting points (but not important) for constant bit rate |
| 163 |
|
|
# |
| 164 |
|
|
IQSCALE 8 |
| 165 |
|
|
PQSCALE 10 |
| 166 |
|
|
BQSCALE 25 |
| 167 |
|
|
|
| 168 |
|
|
# this must be ORIGINAL or DECODED |
| 169 |
|
|
REFERENCE_FRAME DECODED |
| 170 |
|
|
|
| 171 |
|
|
# for parallel parameters see parallel.param in the exmaples subdirectory |
| 172 |
|
|
|
| 173 |
|
|
# if you want constant bit-rate mode, specify it as follows (number is bits/sec): |
| 174 |
|
|
#BIT_RATE 2000000 |
| 175 |
|
|
|
| 176 |
|
|
# To specify the buffer size (327680 is default, measused in bits, for 16bit words) |
| 177 |
|
|
#BUFFER_SIZE 800000 |
| 178 |
|
|
|
| 179 |
|
|
# The frame rate is the number of frames/second (legal values: |
| 180 |
|
|
# 23.976, 24, 25, 29.97, 30, 50 ,59.94, 60 |
| 181 |
|
|
FRAME_RATE $fps |
| 182 |
|
|
|
| 183 |
|
|
# There are many more options, see the users manual for examples.... |
| 184 |
|
|
# ASPECT_RATIO, USER_DATA, GAMMA, IQTABLE, etc. |
| 185 |
|
|
|
| 186 |
|
|
#PARALLEL_TEST_FRAMES 3 |
| 187 |
|
|
#PARALLEL_CHUNK_TAPER |
| 188 |
|
|
|
| 189 |
|
|
#PARALLEL |
| 190 |
|
|
#localhost1 root $mpegencode |
| 191 |
|
|
#localhost2 root $mpegencode |
| 192 |
|
|
#END_PARALLEL |
| 193 |
|
|
|
| 194 |
|
|
EOF |
| 195 |
|
|
|
| 196 |
|
|
close TEMPLATE; |
| 197 |
|
|
|
| 198 |
|
|
$ENV{HOST} = "localhost"; |
| 199 |
|
|
system $mpegencode, "-quiet", "10", "$tmpdir/param"; |
| 200 |
|
|
} |
| 201 |
|
|
|
| 202 |
|
|
my ($frame, $pstart, $pframe) = (0, 0, 0); |
| 203 |
|
|
|
| 204 |
|
|
Video::RTjpeg::init_decompress("x" x (128*4), $w, $h); |
| 205 |
|
|
while (my ($buf, $framex) = next_frame) { |
| 206 |
|
|
print "."; |
| 207 |
|
|
while ($frame < $framex) { |
| 208 |
|
|
if ($pframe == $partlen) { |
| 209 |
|
|
do_encode $pstart, $pframe; |
| 210 |
|
|
$pstart = $frame; |
| 211 |
|
|
$pframe = 0; |
| 212 |
|
|
} |
| 213 |
|
|
#$buf2 = Video::RTjpeg::yuvrgb($buf); open DISPLAY, "| display -size ${w}x$h rgb:-" or die; print DISPLAY $buf2; close DISPLAY; |
| 214 |
|
|
open FRAME, sprintf ">$tmpdir/frame%06d.yuv", $pframe; |
| 215 |
|
|
print FRAME $buf; |
| 216 |
|
|
close FRAME; |
| 217 |
|
|
$frame++; |
| 218 |
|
|
$pframe++; |
| 219 |
|
|
print "s" if $frame != $framex; |
| 220 |
|
|
} |
| 221 |
|
|
last if $frame >= $nframe; |
| 222 |
|
|
} |
| 223 |
|
|
|
| 224 |
|
|
do_encode $pstart, $pframe; |
| 225 |
|
|
|