Running a Cuda program from a Tcl loop

I'm into High Definition video filming and processing, and wanted to get a fast Cuda based image filter to act on a number of frames of some HD footage I shot, so of course I called for the help of a Tcl program.

I appears a command line version foa cuda 1.3 filter program can be run with no problems reported thus far from a normal tcl script (version 8.5, on Fedora 10/64) with simple tricks:

 foreach i [lsort -dict [glob /T/home/theo/Fc10/Frames/00*.ppm]] {
   set im [file tail $i]
   puts -nonewline " $im "
   flush stdout
   exec ~theo/Cuda/C/bin/linux/release/recursiveGaussian -image=$im -sigma=0.3 -qatest << "\n"

   exec mv lena_10.ppm /T/home/theo/Fc10/Frames/cu/$im
   puts -nonewline ","
   flush stdout
 }

Clearly a hack, but now I get gaussian filtred 1829x1080 HD frames automatically from a set of recorded frames, with such a heay filter run in under as second per invocation+result save (The cude smoothing filter itself runs over 12 per second on the machine). For those who want to experiment with this here is the diff from the cuda program compared with the 1.3 devkit:

 80c80
 < float sigma = 0.333f;
 ---
 > float sigma = 10.0f;
 390,391d389
 < //    sigma += 4;
 < 
 397a396
 >     while (sigma <= 22) {    
 404d402
 <     cutilCheckError( cutStopTimer( timer));
 406c404,406
 < //            g_TotalErrors++;
 ---
 >         if (!g_CheckRender->PPMvsPPM(sOriginal[g_Index], sReference[g_Index], MAX_EPSILON_ERROR, THRESHOLD)) {
 >             g_TotalErrors++;
 >         }
 407a408,409
 >         sigma += 4;
 >     }
 408a411
 >     cutilCheckError( cutStopTimer( timer));

Nothing all too fancy.

This approach would also work with BWise as processing block interface, which I think could be cool.

Example frame just after smoothing:

Image TV Wiki 00000033.jpg

Other frame after additonal postprocessing and playing back mp4 of that:

Image TV Wiki ScreenshotUntitledWindow.png

For those interested in this type of High Definition video processing using Free and Open Source software (except VDPau is only open Interface) these are some of the commands I used, which could be put in a tcl/Tk script, but they tend all to write info to stdout, and request input data at some points, so it becomes a bit unhandy at times:

 # Get the HD vid fromthe camera over firewire
 dvgrab  -f mpeg2 > snow2.mpg

 # Play the HD video on screen with VDpau and some additonal settings at 1 frame per second
  mplayer -vo  vdpau:deint=4:denoise=0.7:sharpen=0.86 -noslices -softvol -ao jack:name=mplay2  -af volume=-11 -cache 128000 -contrast +5 -brightness -2 -saturation 70  -fs -fps 1 snow2.mpg

 # capture the above,this writes frames from a 1080HD screen (WUXGA, actually)
  ffmpeg -f x11grab -s 1920x1080 -r 1  -i :0.0+0,60 -r 1  %8d.ppm

 # At this point the above script was run over the frames to create gaussian filtered frames

 # Now a lossless h264 transcoding was done (to try it out), the following three commands are executed in parallel
 ffmpeg -r 25 -i cu/%8d.ppm -r 25  -pix_fmt yuv420p -f yuv4mpegpipe -s 1920x1080 -aspect 16:9 - > /tmp/t.y4m &
 x264 -q 0 --merange 512 --interlace -o /tmp/u.264  /tmp/t.y4m 1920x1080 &
 ffmpeg -i /tmp/u.264 -b 40M -deinterlace -aspect 16:9 -s 1920x1080 snowpaufrcuht.mp4 &

Above are resulting frames from during this process of a quickly recorded snow fragment. He tools above are all required in fairly recent (cvs head, or what is that called currently) version,. and I ran this and the Tcl script on Fedora 10/64. Apart fromall the incidences and the stdio and interaction patters, there is no reason why this all couldn't be scripted and Tk UI-ed.. T result frame was from playing the result with a shader based filter:

 mplayer -vo gl:yuv=6:lscale=4:cscale=5:filter-strength=1.0  -noslices -softvol -nosound -cache 128000 -contrast -20 -brightness +30 -saturation 40 -vf eq2=0.65:1.0:0.0:1.0:1:1:1:1 -fs snowpaufrcuht.mp4

I used this tiny script to get per-minute images from a big set of HD files of hours of original materials in mpeg2, using ffmpeg:

 foreach i [lsort -dict [glob *.m2t]] {
   exec ffmpeg -i $i -s 1280x720 -r 1/60 S/$i.%02d.png 2> /dev/null > /dev/null < /dev/null
 }

Make sure there is a directory "S" which is where 1280x720 .png will be stored from all the files coming from dvgrab (version 1.3, or it won't get HD) in the current dir. Proably a nier tK?) interface is possible.