简体   繁体   中英

exec doesn't found a file

I'm having problems with the exec php function. When I do:

ls -al /dev/sdf1  

This doesn't found the archive (ls: cannot access /dev/sdf1: No such file or directory), but if I run this command, in console that show me the information. What can I do? That happen even running the php script as a root!!

$mountcommand = "ls -al /dev/$unit  2>&1";
exec("$mountcommand", &$mountoutput, &$mountresult);
print_r($mountoutput);
echo "\n$mountcommand\n\n";

This is in a forked process

Works for me.

The disks:

frayser@gentoo ~/doc/Answers/src/PHP $ disk

sda     111.790 GB
sdb     233.762 GB
sdc     233.762 GB
sdd     233.762 GB
sde     279.481 GB
------------------
Total:  1092.558 GB

Using hde:

frayser@gentoo ~/doc/Answers/src/PHP $ l /dev/sde
brw-rw---- 1 root disk 8, 64 Dec  2 13:36 /dev/sde

Using PHP:

frayser@gentoo ~/doc/Answers/src/PHP $ php lsdev.php 
Z: brw-rw---- 1 root disk 8, 64 Dec  2 13:36 /dev/sde

The script:

frayser@gentoo ~/doc/Answers/src/PHP $ cat lsdev.php 
<?php
$z=exec("ls -lr /dev/sde");
print "Z: " . $z . "\n";
?>

Update

It also works with ls -al . Please show your script.

Update 2

Along the lines of the chroot suggestion by ircmaxell: Supposing that /dev, as seen in the PHP process, was a special chroot facsimile of the real one. And supposing that /dev/sdf1 is a removable device. The when sdf1(the media) is inserted the system automatically creates the device in the real /dev; but the chroot version isn't updated. So, to detect this situation look for differences between /dev as seen from PHP and from the commandline.

One test is ls -id on /dev(from PHP and the commandline). This prints the inode of /dev. Is there a mismatch in inode numbers?

Is /dev/sdf1 removable? Is it mounted? If it is mounted; does the PHP process see the mounted filesystem: ls $mount_point from PHP it.

There are other chroot tests listed on Stack Overflow and elsewhere; but I haven found many good ones: If a chroot is done correctly, it is hard to detect.

Update 3

This may be what is happening: The device (/dev/sdf1) takes a while to appear after it is created; so it is necessary to pause between creating the device and attempting to mount it:

Before: The device is created; but it isn't there...

Array
(
    [0] => Logging out of session [sid: 4, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]
    [1] => Logout of [sid: 4, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]: successful
    [2] => Logging in to [iface: iface0, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]
    [3] => Login to [iface: iface0, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]: successful
    [4] => ls: cannot access /dev/sdg: No such file or directory
)

{ test -b /dev/sdg && sudo iscsiadm -m node -T iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e -u; sudo iscsiadm -m node -T iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e -l; ls -al /dev/sdg ;} 2>&1

After: Added a 1-second pause, and the device (sdg) is available...

Array
(
    [0] => Logging out of session [sid: 5, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]
    [1] => Logout of [sid: 5, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]: successful
    [2] => Logging in to [iface: iface0, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]
    [3] => Login to [iface: iface0, target: iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e, portal: 172.16.0.1,3260]: successful
    [4] => brw-rw---- 1 root disk 8, 96 Dec 18 05:27 /dev/sdg
)

{ test -b /dev/sdg && sudo iscsiadm -m node -T iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e -u; sudo iscsiadm -m node -T iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e -l; sleep 1; ls -al /dev/sdg ;} 2>&1

The PHP with the pause ...

<pre>
<?php
$unit='sdg';
$reset="test -b /dev/sdg && sudo iscsiadm -m node -T iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e -u";

$connect="sudo iscsiadm -m node -T iqn.2004-08.org.frayser:gen2-dummy.ad4s0.dos.e -l";

$test="ls -al /dev/$unit";

$mountcommand = "{ $reset; $connect; sleep 1; $test ;} 2>&1";
exec("$mountcommand", $mountoutput, $mountresult);
print_r($mountoutput); 
echo "\n$mountcommand\n\n";
?>
</pre>

The /etc/sudoers is configured the same as reported in the previous question about mount failing from PHP .

So add a second or two of sleep() after iscsiadm creates the device. The sleep can be done in PHP instead of in the exec() of the shell.

我在这段代码和为我提供“单元”的代码之间进行了睡眠修复

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM