I'm writing a simple program to browse the local network and pass on filenames to mplayer using "system". However, sometimes filenames contain spaces or quotes. Obviously I could write my own function to escape those, but I'm not sure exactly what characters do or do not need escaping.
Is there a function available in the CRT or somewhere in the linux headers to safely escape a string to pass to the command line ?
In the platform, the backslash character ( \ ) is used to escape values within strings. The character following the escaping character is treated as a string literal.
"; C# includes escaping character \ (backslash) before these special characters to include in a string. Use backslash \ before double quotes and some special characters such as \,\n,\r,\t, etc. to include it in a string.
Escape sequences are used inside strings, not just those for printf, to represent special characters. In particular, the \n escape sequence represents the newline character.
Other answers include this fork and exec solution, but I claim that this is the only right way to do it.
Escaping shell arguments is prone to bugs and a waste of time, just as trying to escape SQL parameters is a silly idea when safer and more efficient parameter binding APIs exist.
Here is a sample function:
void play(const char *path)
{
/* Fork, then exec */
pid = fork();
if( pid < 0 ) {
/* This is an error! */
return;
}
if( pid == 0 ) {
/* This is the child */
freopen( "/dev/null", "r", stdin );
freopen( "/dev/null", "w", stdout );
freopen( "/dev/null", "w", stderr );
execlp( "mplayer", "mplayer", path, (char *)0 );
/* This is also an error! */
return;
}
}
There isn't a single solution that works everywhere because different shells have different ideas of what special characters are and how they are interpreted. For bash, you could probably get away with surrounding the entire filename in single quotes after replacing every single quote in the file name with '"'"'
(the first single quote stops the sequence, the "'"
appends the literal single quote to the string, the final single quote starts the quoted sequence again). A better solution would be to find a way to call the program without using system, such as by using fork with one of the exec functions so there is no shell interpolation.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With