init脚本'/dev/tty:在重定向时没有这样的设备或地址错误

时间:2021-07-22 20:54:44

I will include the entire script at the bottom for reference. This script gets called toward the end of the init scripts. If I run the script after logging in, it runs with no error. 30000 foot view, trying to execute a rsync command and capture any errors into a variable. I am using bash 3.5.6pl.

我将在底部包含整个脚本以供参考。在init脚本的末尾调用此脚本。如果我在登录后运行脚本,那么它就不会出错。3万英尺视图,尝试执行rsync命令并将错误捕获到一个变量中。我正在使用bash 3.5.6pl。

Here is the line that is the culprit:

这是罪魁祸首:

LogMessage+=$(rsync -rpltDzv --delete --progress /mnt/WinPrimary /mnt/WinBackup 2>&1 >/dev/tty)$'\n'

What is stored in the variable, which does get written to a log, is:

在变量中存储的内容(确实被写入日志)是:

/etc/Braums/scripts/Sync1to2.sh: line 47: /dev/tty: No such device or address

I googled the technique for the syntax to capture stderr but not stdout. I want the progress to show and not capture all the screen stuff. So the init calls the script “Sync1to2.sh”. Which has the above command. If I run the same script from the command line after logging in, it runs as expected.

我在谷歌上搜索了语法技巧以捕获stderr,但没有捕获stdout。我希望进度显示,而不是捕获所有的屏幕内容。因此init调用脚本“Sync1to2.sh”。上面有上述命令。如果我在登录后从命令行运行相同的脚本,它会按预期运行。

Here is the entire Sync1to2.sh script. I don’t do bash scripts too often, so be careful and don’t hurt yourself laughing. One other note, below is when I tried /dev/stdout and it has some diagnostic. I betting it has something to when getty is ran?

这是整个Sync1to2。sh脚本。我不太经常抨击剧本,所以要小心,不要让自己笑得不开心。另一个注意事项是,当我尝试/dev/stdout时,它有一些诊断。我打赌这和盖蒂的计划有关系?

#!/bin/bash
#
#Variable to set if an error occurs at any point during the process.
ErrorOccured="False"
LogMessage=""

LogMessage+=$0$' was stated at '$(date)$'\n'

if !(mount | grep -cq "/mnt/WinPrimary")
then
    LogMessage+=$'=============================================\n'
    LogMessage+=$'][ No Windows Primary found.               ][\n'
    LogMessage+=$'][  Check drives and try again.            ][\n'
    LogMessage+=$'=============================================\n'
    ErrorOccured="True"
fi
if !(mount | grep -cq "/mnt/WinBackup")
then
    LogMessage+=$'=============================================\n'
    LogMessage+=$'][ No Windows Backup found.                ][\n'
    LogMessage+=$'][  Check drives and try again.            ][\n'
    LogMessage+=$'=============================================\n'
    ErrorOccured="True"
fi
if test "$ErrorOccured" == "False"
then
  #Maybe add cleanup the harddrive later
  if [ -f /mnt/WinPrimary/Sync1to2.err ]
  then
    LogMessage+=$'=============================================\n'
    LogMessage+=$'][ Found a Sync1to2.err.                   ][\n'
    LogMessage+=$'][  Are we being run in a loop?            ][\n'
    LogMessage+=$'=============================================\n'
    ErrorOccured="True"
  fi
  if [ -f /mnt/WinPrimary/Sync1to2.ok ]
  then
    LogMessage+=$'=============================================\n'
    LogMessage+=$'][ Found a Sync1to2.ok.                    ][\n'
    LogMessage+=$'][  Are we being run in a loop?            ][\n'
    LogMessage+=$'=============================================\n'
    ErrorOccured="True"
  fi
  if [ "$ErrorOccured" == "False" ]
  then
    LogMessage+=$'Sync Started '$(date)$'\n'
    LogMessage+=$(rsync -rpltDzv --delete --progress /mnt/WinPrimary /mnt/WinBackup 2>&1 >/dev/stdout)$'\n'
    ExitValue=$?
    LogMessage+=$'Sync Finished '$(date)$'\n'
    LogMessage+=$'____________________ '$(date)$'\n'
    LogMessage+=$(ls /dev/tty*)$'\n'
    LogMessage+=$'____________________ '$(date)$'\n'
    LogMessage+=$'____________________ '$(date)$'\n'
    LogMessage+=$(ls /dev/stdout)$'\n'
    LogMessage+=$'____________________ '$(date)$'\n'

    if [ $ExitValue != 0 ]
    then 
      ErrorOccured="True"
    fi
  fi
fi
echo $ErrorOccured
if [ "$ErrorOccured" == "True" ]
then
  echo "Sync1to2 errored out" >> /mnt/WinPrimary/Sync1to2.err
  echo "_______________________________________________________" >> /mnt/WinPrimary/Sync1to2.err
  echo "Finished $(date)" >> /mnt/WinPrimary/Sync1to2.err
  echo "$LogMessage" >> /mnt/WinPrimary/Sync1to2.err
  echo "_______________________________________________________" >> /mnt/WinPrimary/Sync1to2.err
else
  echo "Sync1to2 ok" >> /mnt/WinPrimary/Sync1to2.ok
  echo "_______________________________________________________" >> /mnt/WinPrimary/Sync1to2.ok
  echo "Finished $(date)" >> /mnt/WinPrimary/Sync1to2.ok
  echo "$LogMessage" >> /mnt/WinPrimary/Sync1to2.ok
  echo "_______________________________________________________" >> /mnt/WinPrimary/Sync1to2.ok
  cp /mnt/WinPrimary/menu.default.lst /mnt/WinPrimary/menu.lst
  cp /mnt/WinPrimary/menu.default.lst /mnt/WinBackup/menu.lst
  echo Shuting down
fi
/etc/Braums/scripts/LogPing.pl Sync1to2 "$LogMessage"
exit 254

1 个解决方案

#1


3  

Rather than writing to /dev/tty, how about simply swapping stdout and stderr?

与其写信给/dev/tty,不如简单地交换stdout和stderr?

yourcommand 3>&2 2>&1 1>&3 3>&-

This is the redirection equivalent of swapping the contents of two variables using a third temporary variable:

这相当于使用第三个临时变量交换两个变量的内容:

3>&2  # tmp = stderr 
2>&1  # stderr = stdout
1>&3  # stdout = tmp
3>&-  # close(tmp)

#1


3  

Rather than writing to /dev/tty, how about simply swapping stdout and stderr?

与其写信给/dev/tty,不如简单地交换stdout和stderr?

yourcommand 3>&2 2>&1 1>&3 3>&-

This is the redirection equivalent of swapping the contents of two variables using a third temporary variable:

这相当于使用第三个临时变量交换两个变量的内容:

3>&2  # tmp = stderr 
2>&1  # stderr = stdout
1>&3  # stdout = tmp
3>&-  # close(tmp)