You'll either want to go with preg_match_all(), run the results in a loop and replace whatever you found. Might be a bit faster than the following callback solution, but is a bit more tricky if PREG_OFFSET_CAPUTRE and substr_replace() is used.
<?php
function handle_replace_thingie($matches) {
// build a file path
$file = '/path/to/' . trim($matches[1]);
// do some sanity checks, like file_exists, file-location (not that someone includes /etc/passwd or something)
// check realpath(), file_exists()
// limit the readable files to certain directories
if (false) {
return $matches[0]; // return original, no replacement
}
// assuming the include file outputs its stuff we need to capture it with an output buffer
ob_start();
// execute the include
include $file;
// grab the buffer's contents
$res = ob_get_contents();
ob_end_clean();
// return the contents to replace the original [foo.php]
return $res;
}
$string = "hello world, [my_include.php] and [foo-bar.php] should be replaced";
$string = preg_replace_callback('#\[([^\[]+)\]#', 'handle_replace_thingie', $string);
echo $string, "\n";
?>