/**
  *
  * @param \RainLoop\Model\Account $oAccount
  * @param \MailSo\Mime\Message $oMessage
  * @param resource $rMessageStream
  * @param bool $bDsn = false
  * @param bool $bAddHiddenRcpt = true
  *
  * @throws \RainLoop\Exceptions\ClientException
  * @throws \MailSo\Net\Exceptions\ConnectionException
  */
 private function smtpSendMessage($oAccount, $oMessage, &$rMessageStream, &$iMessageStreamSize, $bDsn = false, $bAddHiddenRcpt = true)
 {
     $oRcpt = $oMessage->GetRcpt();
     if ($oRcpt && 0 < $oRcpt->Count()) {
         $this->Plugins()->RunHook('filter.smtp-message-stream', array($oAccount, &$rMessageStream, &$iMessageStreamSize));
         $this->Plugins()->RunHook('filter.message-rcpt', array($oAccount, &$oRcpt));
         try {
             $oFrom = $oMessage->GetFrom();
             $sFrom = $oFrom instanceof \MailSo\Mime\Email ? $oFrom->GetEmail() : '';
             $sFrom = empty($sFrom) ? $oAccount->Email() : $sFrom;
             $this->Plugins()->RunHook('filter.smtp-from', array($oAccount, $oMessage, &$sFrom));
             $aHiddenRcpt = array();
             if ($bAddHiddenRcpt) {
                 $this->Plugins()->RunHook('filter.smtp-hidden-rcpt', array($oAccount, $oMessage, &$aHiddenRcpt));
             }
             $bUsePhpMail = $oAccount->Domain()->OutUsePhpMail();
             $oSmtpClient = \MailSo\Smtp\SmtpClient::NewInstance()->SetLogger($this->Logger());
             $oSmtpClient->SetTimeOuts(10, (int) \RainLoop\Api::Config()->Get('labs', 'smtp_timeout', 60));
             $bLoggined = $oAccount->OutConnectAndLoginHelper($this->Plugins(), $oSmtpClient, $this->Config(), $bUsePhpMail);
             if ($bUsePhpMail) {
                 if (\MailSo\Base\Utils::FunctionExistsAndEnabled('mail')) {
                     $aToCollection = $oMessage->GetTo();
                     if ($aToCollection && $oFrom) {
                         $sRawBody = @\stream_get_contents($rMessageStream);
                         if (!empty($sRawBody)) {
                             $sMailTo = \trim($aToCollection->ToString(true));
                             $sMailSubject = \trim($oMessage->GetSubject());
                             $sMailSubject = 0 === \strlen($sMailSubject) ? '' : \MailSo\Base\Utils::EncodeUnencodedValue(\MailSo\Base\Enumerations\Encoding::BASE64_SHORT, $sMailSubject);
                             $sMailHeaders = $sMailBody = '';
                             list($sMailHeaders, $sMailBody) = \explode("\r\n\r\n", $sRawBody, 2);
                             unset($sRawBody);
                             if ($this->Config()->Get('labs', 'mail_func_clear_headers', true)) {
                                 $sMailHeaders = \MailSo\Base\Utils::RemoveHeaderFromHeaders($sMailHeaders, array(\MailSo\Mime\Enumerations\Header::TO_, \MailSo\Mime\Enumerations\Header::SUBJECT));
                             }
                             if ($this->Config()->Get('debug', 'enable', false)) {
                                 $this->Logger()->WriteDump(array($sMailTo, $sMailSubject, $sMailBody, $sMailHeaders));
                             }
                             $bR = $this->Config()->Get('labs', 'mail_func_additional_parameters', false) ? \mail($sMailTo, $sMailSubject, $sMailBody, $sMailHeaders, '-f' . $oFrom->GetEmail()) : \mail($sMailTo, $sMailSubject, $sMailBody, $sMailHeaders);
                             if (!$bR) {
                                 throw new \RainLoop\Exceptions\ClientException(\RainLoop\Notifications::CantSendMessage);
                             }
                         }
                     }
                 } else {
                     throw new \RainLoop\Exceptions\ClientException(\RainLoop\Notifications::CantSendMessage);
                 }
             } else {
                 if ($oSmtpClient->IsConnected()) {
                     if (!empty($sFrom)) {
                         $oSmtpClient->MailFrom($sFrom, '', $bDsn);
                     }
                     $aRcpt =& $oRcpt->GetAsArray();
                     foreach ($aRcpt as $oEmail) {
                         $oSmtpClient->Rcpt($oEmail->GetEmail(), $bDsn);
                     }
                     if ($bAddHiddenRcpt && \is_array($aHiddenRcpt) && 0 < \count($aHiddenRcpt)) {
                         foreach ($aHiddenRcpt as $sEmail) {
                             if (\preg_match('/^[^@\\s]+@[^@\\s]+$/', $sEmail)) {
                                 $oSmtpClient->Rcpt($sEmail);
                             }
                         }
                     }
                     $oSmtpClient->DataWithStream($rMessageStream);
                     if ($bLoggined) {
                         $oSmtpClient->Logout();
                     }
                     $oSmtpClient->Disconnect();
                 }
             }
         } catch (\MailSo\Net\Exceptions\ConnectionException $oException) {
             if ($this->Config()->Get('labs', 'smtp_show_server_errors')) {
                 throw new \RainLoop\Exceptions\ClientException(\RainLoop\Notifications::ClientViewError, $oException);
             } else {
                 throw new \RainLoop\Exceptions\ClientException(\RainLoop\Notifications::ConnectionError, $oException);
             }
         } catch (\MailSo\Smtp\Exceptions\LoginException $oException) {
             throw new \RainLoop\Exceptions\ClientException(\RainLoop\Notifications::AuthError, $oException);
         } catch (\Exception $oException) {
             if ($this->Config()->Get('labs', 'smtp_show_server_errors')) {
                 throw new \RainLoop\Exceptions\ClientException(\RainLoop\Notifications::ClientViewError, $oException);
             } else {
                 throw $oException;
             }
         }
     } else {
         throw new \RainLoop\Exceptions\ClientException(\RainLoop\Notifications::InvalidRecipients);
     }
 }