Tag Archives: linux

thread debugging

Valgrind has a thread error detector:

http://valgrind.org/docs/manual/drd-manual.html

mutrace measures mutex contention

http://0pointer.de/blog/projects/mutrace.html

LTTng has a lot of cool features too.

http://lttng.org/

System tap looks interesting too:

https://sourceware.org/systemtap/

 

Video editing in linux

avconv is the new converter to use, ffmpeg is deprecated?!

http://libav.org/avconv.html

guides of interest

Video Editing on Linux

Kdenlive allows you to overlay videos on top of each other.

19 ffmpeg commands for all needs

Published on September 22nd, 2008 by Jean-Baptiste Jung.

http://www.catswhocode.com/blog/19-ffmpeg-commands-for-all-needs

ffmpeg is a multiplatform, open-source library for video and audio files. I have compiled 19 useful and amazing commands covering almost all needs: video conversion, sound extraction, encoding file for iPod or PSP, and more.

Getting infos from a video file

ffmpeg -i video.avi

Turn X images to a video sequence

ffmpeg -f image2 -i image%d.jpg video.mpg

This command will transform all the images from the current directory (named image1.jpg, image2.jpg, etc…) to a video file named video.mpg.

Turn a video to X images

ffmpeg -i video.mpg image%d.jpg

This command will generate the files named image1.jpg, image2.jpg, …

The following image formats are also availables : PGM, PPM, PAM, PGMYUV, JPEG, GIF, PNG, TIFF, SGI.

Encode a video sequence for the iPpod/iPhone

ffmpeg -i source_video.avi input -acodec aac -ab 128kb -vcodec mpeg4 \
     -b 1200kb -mbd 2 -flags +4mv+trell -aic 2 -cmp 2 -subcmp 2 \
     -s 320x180 -title X final_video.mp4

Explanations

Source : source_video.avi
Audio codec : aac
Audio bitrate : 128kb/s
Video codec : mpeg4
Video bitrate : 1200kb/s
Video size : 320px par 180px
Generated video : final_video.mp4

Encode video for the PSP

ffmpeg -i source_video.avi -b 300 -s 320x240 -vcodec xvid -ab 32 -ar 24000 -acodec aac final_video.mp4

Explanations

Source : source_video.avi
Audio codec : aac
Audio bitrate : 32kb/s
Video codec : xvid
Video bitrate : 1200kb/s
Video size : 320px par 180px
Generated video : final_video.mp4

Extracting sound from a video, and save it as Mp3

ffmpeg -i source_video.avi -vn -ar 44100 -ac 2 -ab 192 -f mp3 sound.mp3

Explanations

Source video : source_video.avi
Audio bitrate : 192kb/s
output format : mp3
Generated sound : sound.mp3

Convert a wav file to Mp3

ffmpeg -i son_origine.avi -vn -ar 44100 -ac 2 -ab 192 -f mp3 son_final.mp3

Convert .avi video to .mpg

ffmpeg -i video_origine.avi video_finale.mpg

Convert .mpg to .avi

ffmpeg -i video_origine.mpg video_finale.avi

Convert .avi to animated gif(uncompressed)

ffmpeg -i video_origine.avi gif_anime.gif

Mix a video with a sound file

ffmpeg -i son.wav -i video_origine.avi video_finale.mpg

Convert .avi to .flv

ffmpeg -i video_origine.avi -ab 56 -ar 44100 -b 200 -r 15 -s 320x240 -f flv video_finale.flv

Convert .avi to dv

ffmpeg -i video_origine.avi -s pal -r pal -aspect 4:3 -ar 48000 -ac 2 video_finale.dv

Or:

ffmpeg -i video_origine.avi -target pal-dv video_finale.dv

Convert .avi to mpeg for dvd players

ffmpeg -i source_video.avi -target pal-dvd -ps 2000000000 -aspect 16:9 finale_video.mpeg

Explanations

target pal-dvd : Output format
ps 2000000000 maximum size for the output file, in bits (here, 2 Gb)
aspect 16:9 : Widescreen

Compress .avi to divx

ffmpeg -i video_origine.avi -s 320x240 -vcodec msmpeg4v2 video_finale.avi

Compress Ogg Theora to Mpeg dvd

ffmpeg -i film_sortie_cinelerra.ogm -s 720x576 -vcodec mpeg2video -acodec mp3 film_termine.mpg

Compress .avi to SVCD mpeg2

NTSC format:

ffmpeg -i video_origine.avi -target ntsc-svcd video_finale.mpg

PAL format:

ffmpeg -i video_origine.avi -target pal-svcd video_finale.mpg

Compress .avi to VCD mpeg2

NTSC format:

ffmpeg -i video_origine.avi -target ntsc-vcd video_finale.mpg

PAL format:

ffmpeg -i video_origine.avi -target pal-vcd video_finale.mpg

Multi-pass encoding with ffmpeg

ffmpeg -i fichierentree -pass 2 -passlogfile ffmpeg2pass fichiersortie-2

Mencoder way

it is a two pass.

first

mencoder uncompressedfile.whatever -ovc lavc -lavcopts \
    vcodec=msmpeg4v2:vpass=1:vbitrate=8000000:mbd=2:keyint=132:vqblur=1.0:cmp=2:subcmp=2:dia=2:mv0:last_pred=3 \
    -nosound -o avs.avi

second

mencoder -ovc lavc -lavcopts \
    vcodec=msmpeg4v2:vpass=2:vbitrate=8000000:mbd=2:keyint=132:vqblur=1.0:cmp=2:subcmp=2:dia=2:mv0:last_pred=3 \
    -nosound -o compressedfile.avi avs.avi

old way

mencoder umaps2.avi -o output.mpg -ofps 25 -vf scale=900:720,harddup -of lavf -lavfopts format=mpg \
    -oac lavc -lavcopts acodec=mp2:abitrate=1224 -ovc lavc -lavcopts \
    vcodec=mpeg1video:vrc_buf_size=1327:keyint=15:vrc_maxrate=11152:vbitrate=11152:vmax_b_frames=0

kyle’s way

ffmpeg -i <inputfile.ext> -vcodec msmpeg4v2 -acodec mp3 <file.avi>

website explaining how to encode with mencoder.

http://personal.cscs.ch/~mvalle/mencoder/mencoder.html

 

Imaging drive partitions using tar

Imaging drive partitions using ‘tar’

Boot using a live CD or USB

Mount both partitions. Assumptions:

  • /mnt/a – has linux installed
  • /mnt/b – is empty
  • Running Ubuntu 12.04

tar it up

su -
cd /mnt/a
tar -cf image.tar *
cp image.tar /mnt/b
cd /mnt/b
tar -xf image.tar

set /mnt/b/etc/fstab to point to /mnt/b UUID

- you can get UUID with `blkid` command

rename /mnt/b/boot/grub

- `mv /mnt/b/boot/grub /mnt/b/boot/grub.bak`

boot into /mnt/a

- should be just a restart

update-grub should recognize that there are two bootable partitions

If you need to add kernel parameters like noapic for macs

  • open /boot/grub/grub.cfg
  • find the menu item that boots /mnt/b (should be under OS_PROBER)
  • copy that entry to the end of /etc/grub.d/40_custom
  • add kernel parameter to the line that starts with linux
  • Optionally disable OS_PROBER to keep grub menu clean
    • sudo chmod a-x /etc/grub.d/30_os-prober
  • sudo update-grub
  • check if your configuration worked in /boot/grub/grub.cfg

text to speech options on linux

espeak

eSpeak is a software speech synthesizer for English, and some other
languages.

eSpeak produces good quality English speech. It uses a different synthesis
method from other open source text to speech (TTS) engines, and sounds quite
different. It’s perhaps not as natural or “smooth”, but some find the
articulation clearer and easier to listen to for long periods.

It can run as a command line program to speak text from a file or from stdin.

* Includes different Voices, whose characteristics can be altered.
* Can produce speech output as a WAV file.
* Can translate text to phoneme codes, so it could be adapted as a front end
for another speech synthesis engine.
* Potential for other languages. More than 40 languages are included.
* Compact size. The program and its data total about 350 kbytes.
* Written in C++.

festival

Festival offers a full text to speech system with various APIs, as well an
environment for development and research of speech synthesis techniques. It
includes a Scheme-based command interpreter.

Besides research into speech synthesis, festival is useful as a stand-alone
speech synthesis program. It is capable of producing clearly understandable
speech from text.

flite

Flite is a small fast run-time speech synthesis engine. It is the
latest addition to the suite of free software synthesis tools
including University of Edinburgh’s Festival Speech Synthesis System
and Carnegie Mellon University’s FestVox project, tools, scripts and
documentation for building synthetic voices. However, flite itself
does not require either of these systems to run.

It currently only supports the English language.

linux find command

linux command find does wonders! It has a rich set of options to find any kinds of files and directories and execute commands on those files.

find dirname -name fname

More examples:

find . -name a.out -executable
find . -name *.o -delete
find . -name dirtofind -type d
find . -name filetofind -type f

To execute a command on every file you find:

find . -name *.hh -exec ls -l {} ;

And much more. See man find

pahole shows data structures from debug data in ELF binaries

pahole is a part of dwarves utilities package and can parse structure information from DWARF and CTF fields in your binary executables. Pahole is useful for highlighting data packing discrepancies and cache alignment in data structures. This can be very useful for data structures that are stored in RAM and are accessed by your main bottlenecks. It can particularly come in useful when switching to 64bit machines. It should be used in very very very late stage of optimization 😉

Installation

Ubuntu makes it very easy:

sudo apt-get install dwarves

Example

Let’s write a simple test file:

#include <stdint.h>

struct S {
  struct S*    a;
  struct S*    b;
  uint8_t      c;
  double       d;
  int32_t      e;
  int32_t      f;
  int32_t      g;
  uint16_t     h;
  uint16_t     i;
  float        j;
  int16_t      k;
  int8_t       l;
  double       m;
  int32_t      n;
  double       o;
  int32_t      p;
  double       q;
};

int main(int argc, char ** argv)
{
  struct S s;
  return 0;
}

and compile it with debug flags

g++ -g test.cc

This will produce an executable called a.out. Now we simply run pahole with the newly created executable as an argument.

pahole a.out

The output is fairly informative:

/tmp> pahole a.out
struct S {
	class S *                  a;                    /*     0     4 */
	class S *                  b;                    /*     4     4 */
	uint8_t                    c;                    /*     8     1 */

	/* XXX 3 bytes hole, try to pack */

	double                     d;                    /*    12     8 */
	int32_t                    e;                    /*    20     4 */
	int32_t                    f;                    /*    24     4 */
	int32_t                    g;                    /*    28     4 */
	uint16_t                   h;                    /*    32     2 */
	uint16_t                   i;                    /*    34     2 */
	float                      j;                    /*    36     4 */
	int16_t                    k;                    /*    40     2 */
	int8_t                     l;                    /*    42     1 */

	/* XXX 1 byte hole, try to pack */

	double                     m;                    /*    44     8 */
	int32_t                    n;                    /*    52     4 */
	double                     o;                    /*    56     8 */
	/* --- cacheline 1 boundary (64 bytes) --- */
	int32_t                    p;                    /*    64     4 */
	double                     q;                    /*    68     8 */

	/* size: 76, cachelines: 2 */
	/* sum members: 72, holes: 2, sum holes: 4 */
	/* last cacheline: 12 bytes */
};	/* definitions: 1 */

Linux Scheduler

Mainline linux kernel distribution received a number of real-time additions over that last few years. More details on OASDL site. Here is my small experiment with a program that changes it’s own scheduling policy and example on how to see traced kernel events using ftrace.

Example below shows how to change scheduling policy from within the program itself. Note, if the scheduling policy does not change at runtime a perhaps cleaner and easier solution is provided via schedtool (command line tool).

#include <sched.h>
#include <stdio.h>
#include <unistd.h>

const char * ParsePolicy(int policy)
{
  switch (policy){
  case SCHED_FIFO  : return "SCHED_FIFO";
  case SCHED_RR    : return "SCHED_RR";
  case SCHED_OTHER : return "SCHED_OTHER";
  case SCHED_BATCH : return "SCHED_BATCH";
  default : return "Did not recognize policy";
  }
}

int GetPolicy()
{
  int policy = sched_getscheduler(0);
  if (policy == -1){
    perror(__FUNCTION__);
    return -1;
  }

  fprintf(stdout, "%s - %sn", __FUNCTION__, ParsePolicy(policy));

  return policy;
}

int SetPolicy(int policy)
{
  pid_t pid = getpid();
  fprintf(stdout, "pid = %dn", (int)pid);

  fprintf(stdout, "%s - %sn", __FUNCTION__, ParsePolicy(policy));

  struct sched_param param;
  param.sched_priority = sched_get_priority_max(policy);

  fprintf(stdout, "max priority = %dn", param.sched_priority);

  int setsch = sched_setscheduler(pid, policy, &amp;param);
  if (setsch == -1)
    perror(__FUNCTION__);

  return setsch; // 0 - OK, -1 - fail
}

long long BusyWait(long long cycles)
{
  while(cycles)
    cycles--;
  return cycles;
}

int main()
{
  GetPolicy();

  long long wait = 200000000;

  SetPolicy(SCHED_FIFO);
  GetPolicy();
  BusyWait(wait);

  SetPolicy(SCHED_RR);
  GetPolicy();
  BusyWait(wait);

  SetPolicy(SCHED_OTHER);
  GetPolicy();
  BusyWait(wait);

  SetPolicy(SCHED_BATCH);
  GetPolicy();
  BusyWait(wait);

  return 0;
}

Since the program uses a simple while counter as a busy wait, you need to compile it without optimization flags.

  gcc -Wall -O0 test_schedule.c -o test_schedule

Now, in order to actually see what is happenning under the hood, we use ftrace (tracing functionality built-in in most newer kernels), trace-cmd, and kernelshark. These packages are in default Ubuntu repositories and can be installed with "sudo apt-get install trace-cmd kernelshark".

trace-cmd has many useful options. I suggest reading the man page. In this case, I will show a simple use case for the example above. We will run trace command that will execute the scheduler test from above and store scheduling info.

sudo trace-cmd record -e sched ./test_schedule

This command saves trace.dat, and shows output that looks like this:

$ sudo trace-cmd record -e sched ./test_schedule
disable all
enable sched
path = /sys/kernel/debug/tracing/events/sched/enable
path = /sys/kernel/debug/tracing/events/*/sched/enable
GetPolicy - SCHED_OTHER
pid = 10628
SetPolicy - SCHED_FIFO
max priority = 99
GetPolicy - SCHED_FIFO
pid = 10628
SetPolicy - SCHED_RR
max priority = 99
GetPolicy - SCHED_RR
pid = 10628
SetPolicy - SCHED_OTHER
max priority = 0
GetPolicy - SCHED_OTHER
pid = 10628
SetPolicy - SCHED_BATCH
max priority = 0
GetPolicy - SCHED_BATCH
offset=535000
offset=575000
offset=700000
offset=886000
offset=9ea000
offset=9f9000
offset=b57000
offset=cbc000
Kernel buffer statistics:
  Note: "entries" are the entries left in the kernel ring buffer and are not
        recorded in the trace data. They should all be zero.

CPU: 0
entries: 0
overrun: 0
commit overrun: 0
bytes: 2708
oldest event ts: 274629.435366
now ts: 274630.751883

CPU: 1
entries: 0
overrun: 0
commit overrun: 0
bytes: 2620
oldest event ts: 274630.577012
now ts: 274630.752018

CPU: 2
entries: 0
overrun: 0
commit overrun: 0
bytes: 1056
oldest event ts: 274630.581643
now ts: 274630.752128

CPU: 3
entries: 0
overrun: 0
commit overrun: 0
bytes: 3020
oldest event ts: 274630.578163
now ts: 274630.752241

CPU: 4
entries: 0
overrun: 0
commit overrun: 0
bytes: 3872
oldest event ts: 274630.514477
now ts: 274630.752359

CPU: 5
entries: 0
overrun: 0
commit overrun: 0
bytes: 1728
oldest event ts: 274630.579316
now ts: 274630.752472

CPU: 6
entries: 0
overrun: 0
commit overrun: 0
bytes: 852
oldest event ts: 274630.581604
now ts: 274630.752558

CPU: 7
entries: 0
overrun: 0
commit overrun: 0
bytes: 2300
oldest event ts: 274630.574664
now ts: 274630.752643

trace.dat is a file readable by kernelshark

If we start kernelshark in the same directory, it will automatically open trace.dat and we can closely analyze events that happened during this run.

Useful links: