GetOne("SELECT client FROM tf_transfers WHERE transfer = ".$db->qstr($transfer)); if (empty($client)) { if (substr($transfer, -8) == ".torrent") { // this is a torrent-client $client = $cfg["btclient"]; } else if (substr($transfer, -5) == ".wget") { // this is wget. $client = "wget"; } else if (substr($transfer, -4) == ".nzb") { // This is nzbperl. $client = "nzbperl"; } else { $client = $cfg["btclient"]; } } $transfers['settings'][$transfer]['client'] = $client; return $client; } } /** * getRunningTransferCount * * @return int with number of running transfers */ function getRunningTransferCount() { global $cfg; // use pid-files-direct-access for now because all clients of currently // available handlers write one. then its faster and correct meanwhile. if ($dirHandle = @opendir($cfg["transfer_file_path"])) { $tCount = 0; while (false !== ($file = @readdir($dirHandle))) { if ((substr($file, -4, 4)) == ".pid") $tCount++; } @closedir($dirHandle); return $tCount; } else { return 0; } } /** * get the full size of a transfer * * @param $transfer * @return int */ function getTransferSize($transfer) { global $cfg; // client-switch if (substr($transfer, -8) == ".torrent") { // this is a t-client $file = $cfg["transfer_file_path"].$transfer; if ($fd = @fopen($file, "rd")) { require_once("inc/classes/BDecode.php"); $alltorrent = @fread($fd, @filesize($file)); $array = @BDecode($alltorrent); @fclose($fd); } return ((isset($array["info"]["piece length"])) && (isset($array["info"]["pieces"]))) ? $array["info"]["piece length"] * (strlen($array["info"]["pieces"]) / 20) : 0; } else if (substr($transfer, -5) == ".wget") { // this is wget. $ch = ClientHandler::getInstance('wget'); $ch->setVarsFromFile($transfer); require_once("inc/classes/SimpleHTTP.php"); return SimpleHTTP::getRemoteSize($ch->url); } else if (substr($transfer, -4) == ".nzb") { // this is nzbperl. require_once("inc/classes/NZBFile.php"); $nzb = new NZBFile($transfer); return $nzb->size; } return 0; } /** * gets hash of a transfer * * @param $transfer name of the transfer * @return transfer-hash */ function getTransferHash($transfer) { global $cfg, $db, $transfers; if (isset($transfers['settings'][$transfer]['hash'])) { return $transfers['settings'][$transfer]['hash']; } else { $hash = $db->GetOne("SELECT hash FROM tf_transfers WHERE transfer = ".$db->qstr($transfer)); if (empty($hash)) { if (substr($transfer, -8) == ".torrent") { // this is a torrent-client $metainfo = getTorrentMetaInfo($transfer); if (empty($metainfo)) { $hash = ""; } else { $resultAry = explode("\n", $metainfo); $hashAry = array(); switch ($cfg["metainfoclient"]) { case "transmissioncli": case "ttools.pl": $hashAry = explode(":", trim($resultAry[0])); break; case "btshowmetainfo.py": case "torrentinfo-console.py": default: $hashAry = explode(":", trim($resultAry[3])); break; } $hash = (isset($hashAry[1])) ? trim($hashAry[1]) : ""; } } else if (substr($transfer, -5) == ".wget") { // this is wget. $metacontent = @file_get_contents($cfg["transfer_file_path"].$transfer); $hash = (empty($metacontent)) ? "" : sha1($metacontent); } else if (substr($transfer, -4) == ".nzb") { // This is nzbperl. $metacontent = @file_get_contents($cfg["transfer_file_path"].$transfer); $hash = (empty($metacontent)) ? "" : sha1($metacontent); } else { $hash = ""; } } $transfers['settings'][$transfer]['hash'] = $hash; return $hash; } } /** * gets metainfo of a torrent as string * * @param $transfer name of the torrent * @return string with torrent-meta-info */ function getTorrentMetaInfo($transfer) { global $cfg; switch ($cfg["metainfoclient"]) { case "transmissioncli": return shell_exec("HOME=".tfb_shellencode($cfg["path"])."; export HOME; ".$cfg["btclient_transmission_bin"]." -i ".tfb_shellencode($cfg["transfer_file_path"].$transfer)); case "ttools.pl": return shell_exec($cfg["perlCmd"].' -I '.tfb_shellencode($cfg["docroot"].'bin/ttools').' '.tfb_shellencode($cfg["docroot"].'bin/ttools/ttools.pl').' -i '.tfb_shellencode($cfg["transfer_file_path"].$transfer)); case "torrentinfo-console.py": return shell_exec("cd ".tfb_shellencode($cfg["transfer_file_path"])."; ".$cfg["pythonCmd"]." -OO ".tfb_shellencode($cfg["docroot"]."bin/clients/mainline/torrentinfo-console.py")." ".tfb_shellencode($transfer)); case "btshowmetainfo.py": default: return shell_exec("cd ".tfb_shellencode($cfg["transfer_file_path"])."; ".$cfg["pythonCmd"]." -OO ".tfb_shellencode($cfg["docroot"]."bin/clients/tornado/btshowmetainfo.py")." ".tfb_shellencode($transfer)); } } /** * gets details of a transfer as array * * @param $transfer * @param $full * @return array with details * * array-keys : * * running * speedDown * speedUp * downCurrent * upCurrent * downTotal * upTotal * percentDone * sharing * timeLeft * seeds * peers * cons * * owner * size * maxSpeedDown * maxSpeedUp * maxcons * sharekill * port * */ function getTransferDetails($transfer, $full) { global $cfg, $transfers; $details = array(); // common functions require_once('inc/functions/functions.common.php'); $transferowner = getOwner($transfer); // stat $sf = new StatFile($transfer, $transferowner); // settings if (isset($transfers['settings'][$transfer])) { $settingsAry = $transfers['settings'][$transfer]; } else { $settingsAry = array(); if (substr($transfer, -8) == ".torrent") { // this is a t-client $settingsAry['type'] = "torrent"; $settingsAry['client'] = $cfg["btclient"]; } else if (substr($transfer, -5) == ".wget") { // this is wget. $settingsAry['type'] = "wget"; $settingsAry['client'] = "wget"; } else if (substr($transfer, -4) == ".nzb") { // this is nzbperl. $settingsAry['type'] = "nzb"; $settingsAry['client'] = "nzbperl"; } else { AuditAction($cfg["constants"]["error"], "INVALID TRANSFER: ".$transfer); @error("Invalid Transfer", "", "", array($transfer)); } $settingsAry['hash'] = ""; $settingsAry["savepath"] = ($cfg["enable_home_dirs"] != 0) ? $cfg["path"].$transferowner.'/' : $cfg["path"].$cfg["path_incoming"].'/'; $settingsAry['datapath'] = ""; } // size $size = floatval($sf->size); // totals $afu = $sf->uptotal; $afd = $sf->downtotal; $ch = ClientHandler::getInstance($settingsAry['client']); $totalsCurrent = $ch->getTransferCurrentOP($transfer, $settingsAry['hash'], $afu, $afd); $totals = $ch->getTransferTotalOP($transfer, $settingsAry['hash'], $afu, $afd); // running $running = $sf->running; $details['running'] = $running; // speed_down + speed_up + seeds + peers + cons if ($running == 1) { // pid $pid = getTransferPid($transfer); // speed_down $details['speedDown'] = (trim($sf->down_speed) != "") ? $sf->down_speed : '0.0 kB/s'; // speed_up $details['speedUp'] = (trim($sf->up_speed) != "") ? $sf->up_speed : '0.0 kB/s'; // down_current $details['downCurrent'] = @formatFreeSpace($totalsCurrent["downtotal"] / 1048576); // up_current $details['upCurrent'] = @formatFreeSpace($totalsCurrent["uptotal"] / 1048576); // seeds $details['seeds'] = $sf->seeds; // peers $details['peers'] = $sf->peers; // cons $details['cons'] = netstatConnectionsByPid($pid); } else { // speed_down $details['speedDown'] = ""; // speed_up $details['speedUp'] = ""; // down_current $details['downCurrent'] = ""; // up_current $details['upCurrent'] = ""; // seeds $details['seeds'] = ""; // peers $details['peers'] = ""; // cons $details['cons'] = ""; } // down_total $details['downTotal'] = @formatFreeSpace($totals["downtotal"] / 1048576); // up_total $details['upTotal'] = @formatFreeSpace($totals["uptotal"] / 1048576); // percentage $percentage = $sf->percent_done; if ($percentage < 0) { $percentage = round(($percentage * -1) - 100, 1); $sf->time_left = $cfg['_INCOMPLETE']; } elseif ($percentage > 100) { $percentage = 100; } $details['percentDone'] = $percentage; // eta $details['eta'] = $sf->time_left; // sharing $details['sharing'] = ($totals["downtotal"] > 0) ? @number_format((($totals["uptotal"] / $totals["downtotal"]) * 100), 2) : 0; // full (including static) details if ($full) { // owner $details['owner'] = $transferowner; // size $details['size'] = @formatBytesTokBMBGBTB($size); if ($running == 1) { // max_download_rate $details['maxSpeedDown'] = number_format($cfg["max_download_rate"], 2); // max_upload_rate $details['maxSpeedUp'] = number_format($cfg["max_upload_rate"], 2); // maxcons $details['maxcons'] = $cfg["maxcons"]; // sharekill $details['sharekill'] = $cfg["sharekill"]; // port $details['port'] = netstatPortByPid($pid); } else { // max_download_rate $details['maxSpeedDown'] = ""; // max_upload_rate $details['maxSpeedUp'] = ""; // maxcons $details['maxcons'] = ""; // sharekill $details['sharekill'] = ""; // port $details['port'] = ""; } } // return return $details; } /** * This method gets transfers from database in an array * * @return array with transfers */ function getTransferArrayFromDB() { global $db; $retVal = array(); $sql = "SELECT transfer FROM tf_transfers ORDER BY transfer ASC"; $recordset = $db->Execute($sql); if ($db->ErrorNo() != 0) dbError($sql); while(list($transfer) = $recordset->FetchRow()) array_push($retVal, $transfer); return $retVal; } /** * This method gets transfers in an array * * @param $sortOrder * @return array */ function getTransferArray($sortOrder = '') { global $cfg; $retVal = array(); $handle = @opendir($cfg["transfer_file_path"]); if (!$handle) { AuditAction($cfg["constants"]["error"], "error when opening transfers-dir ".$cfg["transfer_file_path"]); return $retVal; } while ($transfer = @readdir($handle)) { if ($transfer{0} != ".") { switch (substr($transfer, -4)) { case 'stat': case '.log': case '.pid': case '.cmd': case 'prio': break; default: if (tfb_isValidTransfer($transfer)) $retVal[filemtime($cfg["transfer_file_path"].$transfer).md5($transfer)] = $transfer; else AuditAction($cfg["constants"]["error"], "INVALID TRANSFER: ".$transfer); break; } } } @closedir($handle); // sort transfer-array $sortId = ($sortOrder != "") ? $sortOrder : $cfg["index_page_sortorder"]; switch ($sortId) { case 'da': // sort by date ascending ksort($retVal); break; case 'dd': // sort by date descending krsort($retVal); break; case 'na': // sort alphabetically by name ascending natcasesort($retVal); break; case 'nd': // sort alphabetically by name descending natcasesort($retVal); $retVal = array_reverse($retVal, true); break; } return $retVal; } /** * This method gets the head of the transfer-list * * @param $settings * @return transfer-list-head array */ function getTransferListHeadArray($settings = null) { global $cfg; // settings if (!(isset($settings))) $settings = convertIntegerToArray($cfg["index_page_settings"]); // retval $retVal = array(); // =================================================================== owner if ($settings[0] != 0) array_push($retVal, $cfg['_USER']); // ==================================================================== size if ($settings[1] != 0) array_push($retVal, "Size"); // =============================================================== downtotal if ($settings[2] != 0) array_push($retVal, "T. Down"); // ================================================================= uptotal if ($settings[3] != 0) array_push($retVal, "T. Up"); // ================================================================== status if ($settings[4] != 0) array_push($retVal, "Status"); // ================================================================ progress if ($settings[5] != 0) array_push($retVal, "Progress"); // ==================================================================== down if ($settings[6] != 0) array_push($retVal, "Down"); // ====================================================================== up if ($settings[7] != 0) array_push($retVal, "Up"); // =================================================================== seeds if ($settings[8] != 0) array_push($retVal, "Seeds"); // =================================================================== peers if ($settings[9] != 0) array_push($retVal, "Peers"); // ===================================================================== ETA if ($settings[10] != 0) array_push($retVal, "Estimated Time"); // ================================================================== client if ($settings[11] != 0) array_push($retVal, "Client"); // return return $retVal; } /** * This method gets the list of transfer * * @return array */ function getTransferListArray() { global $cfg, $db, $transfers; $kill_id = ""; $lastUser = ""; $arUserTransfers = array(); $arListTransfers = array(); // settings $settings = convertIntegerToArray($cfg["index_page_settings"]); // sortOrder $sortOrder = tfb_getRequestVar("so"); if ($sortOrder == "") $sortOrder = $cfg["index_page_sortorder"]; // t-list $arList = getTransferArray($sortOrder); foreach ($arList as $transfer) { // init some vars $displayname = $transfer; $show_run = true; $transferowner = getOwner($transfer); $owner = IsOwner($cfg["user"], $transferowner); // stat $sf = new StatFile($transfer, $transferowner); // settings if (isset($transfers['settings'][$transfer])) { $settingsAry = $transfers['settings'][$transfer]; } else { $settingsAry = array(); if (substr($transfer, -8) == ".torrent") { // this is a t-client $settingsAry['type'] = "torrent"; $settingsAry['client'] = $cfg["btclient"]; } else if (substr($transfer, -5) == ".wget") { // this is wget. $settingsAry['type'] = "wget"; $settingsAry['client'] = "wget"; } else if (substr($transfer, -4) == ".nzb") { // this is nzbperl. $settingsAry['type'] = "nzb"; $settingsAry['client'] = "nzbperl"; } else { AuditAction($cfg["constants"]["error"], "INVALID TRANSFER: ".$transfer); @error("Invalid Transfer", "", "", array($transfer)); } $settingsAry['hash'] = ""; $settingsAry["savepath"] = ($cfg["enable_home_dirs"] != 0) ? $cfg["path"].$transferowner.'/' : $cfg["path"].$cfg["path_incoming"].'/'; $settingsAry['datapath'] = ""; } // cache running-flag in local var. we will access that often $transferRunning = $sf->running; // cache percent-done in local var. ... $percentDone = $sf->percent_done; // --------------------------------------------------------------------- //XFER: update1: add upload/download stats to the xfer array if (($cfg['enable_xfer'] == 1) && ($cfg['xfer_realtime'] == 1)) @Xfer::update1($transfer, $transferowner, $settingsAry['client'], $settingsAry['hash'], $sf->uptotal, $sf->downtotal); // --------------------------------------------------------------------- // injects if (!file_exists($cfg["transfer_file_path"].$transfer.".stat")) { $transferRunning = 2; $sf->running = "2"; $sf->size = getTransferSize($transfer); injectTransfer($transfer); } // totals-preparation // if downtotal + uptotal + progress > 0 if (($settings[2] + $settings[3] + $settings[5]) > 0) { $ch = ClientHandler::getInstance($settingsAry['client']); $transferTotals = $ch->getTransferTotalOP($transfer, $settingsAry['hash'], $sf->uptotal, $sf->downtotal); } // --------------------------------------------------------------------- // preprocess stat-file and get some vars $estTime = ""; $statusStr = ""; switch ($transferRunning) { case 2: // new $statusStr = 'New'; break; case 3: // queued $statusStr = 'Queued'; $estTime = 'Waiting'; break; default: // running + stopped // increment the totals if (!isset($cfg["total_upload"])) $cfg["total_upload"] = 0; if (!isset($cfg["total_download"])) $cfg["total_download"] = 0; $cfg["total_upload"] = $cfg["total_upload"] + GetSpeedValue($sf->up_speed); $cfg["total_download"] = $cfg["total_download"] + GetSpeedValue($sf->down_speed); // $estTime if ($transferRunning == 0) { $estTime = $sf->time_left; } else { if ($sf->time_left != "" && $sf->time_left != "0") { if (($cfg["display_seeding_time"] == 1) && ($sf->percent_done >= 100) ) { $estTime = (($sf->seedlimit > 0) && (!empty($sf->up_speed)) && (intval(($sf->up_speed{0})) > 0)) ? convertTime(((($sf->seedlimit) / 100 * $sf->size) - $sf->uptotal) / GetSpeedInBytes($sf->up_speed)) : '-'; } else { $estTime = $sf->time_left; } } } // $lastUser $lastUser = $transferowner; // $show_run + $statusStr if($percentDone >= 100) { $statusStr = (($transferRunning == 1) && (trim($sf->up_speed) != "")) ? 'Seeding' : 'Done'; $show_run = false; } else if ($percentDone < 0) { $statusStr = 'Stopped'; $show_run = true; } else { $statusStr = 'Leeching'; } break; } // --------------------------------------------------------------------- // fill temp array $transferAry = array(); // ================================================================ name array_push($transferAry, $transfer); // =============================================================== owner if ($settings[0] != 0) array_push($transferAry, $transferowner); // ================================================================ size if ($settings[1] != 0) array_push($transferAry, @formatBytesTokBMBGBTB($sf->size)); // =========================================================== downtotal if ($settings[2] != 0) array_push($transferAry, @formatBytesTokBMBGBTB($transferTotals["downtotal"])); // ============================================================= uptotal if ($settings[3] != 0) array_push($transferAry, @formatBytesTokBMBGBTB($transferTotals["uptotal"])); // ============================================================== status if ($settings[4] != 0) array_push($transferAry, $statusStr); // ============================================================ progress if ($settings[5] != 0) { $percentage = ""; if (($percentDone >= 100) && (trim($sf->up_speed) != "")) { $percentage = @number_format((($transferTotals["uptotal"] / $sf->size) * 100), 2) . '%'; } else { if ($percentDone >= 1) $percentage = $percentDone . '%'; else if ($percentDone < 0) $percentage = round(($percentDone*-1)-100,1) . '%'; else $percentage = '0%'; } array_push($transferAry, $percentage); } // ================================================================ down if ($settings[6] != 0) { $down = ""; if ($transferRunning == 1) $down = (trim($sf->down_speed) != "") ? $sf->down_speed : '0.0 kB/s'; array_push($transferAry, $down); } // ================================================================== up if ($settings[7] != 0) { $up = ""; if ($transferRunning == 1) $up = (trim($sf->up_speed) != "") ? $sf->up_speed : '0.0 kB/s'; array_push($transferAry, $up); } // =============================================================== seeds if ($settings[8] != 0) { $seeds = ($transferRunning == 1) ? $sf->seeds : ""; array_push($transferAry, $seeds); } // =============================================================== peers if ($settings[9] != 0) { $peers = ($transferRunning == 1) ? $sf->peers : ""; array_push($transferAry, $peers); } // ================================================================= ETA if ($settings[10] != 0) array_push($transferAry, $estTime); // ============================================================== client if ($settings[11] != 0) { switch ($settingsAry['client']) { case "tornado": array_push($transferAry, "B"); break; case "transmission": array_push($transferAry, "T"); break; case "mainline": array_push($transferAry, "M"); break; case "azureus": array_push($transferAry, "A"); break; case "wget": array_push($transferAry, "W"); break; case "nzbperl": array_push($transferAry, "N"); break; default: array_push($transferAry, "U"); } } // --------------------------------------------------------------------- // Is this transfer for the user list or the general list? if ($owner) array_push($arUserTransfers, $transferAry); else array_push($arListTransfers, $transferAry); } //XFER: update 2 if (($cfg['enable_xfer'] == 1) && ($cfg['xfer_realtime'] == 1)) @Xfer::update2(); // ------------------------------------------------------------------------- // build output-array $retVal = array(); if (sizeof($arUserTransfers) > 0) { foreach($arUserTransfers as $torrentrow) array_push($retVal, $torrentrow); } $boolCond = true; if ($cfg['enable_restrictivetview'] == 1) $boolCond = $cfg['isAdmin']; if (($boolCond) && (sizeof($arListTransfers) > 0)) { foreach($arListTransfers as $torrentrow) array_push($retVal, $torrentrow); } return $retVal; } /** * Function to load the owner for all transfers. returns ref to array * * @return array-ref */ function &loadAllTransferOwner() { $ary = array(); $tary = getTransferArray(); foreach ($tary as $transfer) $ary[$transfer] = getOwner($transfer); return $ary; } /** * Function to load the totals for all transfers. returns ref to array * * @return array-ref */ function &loadAllTransferTotals() { global $db; $recordset = $db->Execute("SELECT * FROM tf_transfer_totals"); $ary = array(); while ($row = $recordset->FetchRow()) { if (strlen($row["tid"]) == 40) { $ary[$row["tid"]] = array( "uptotal" => $row["uptotal"], "downtotal" => $row["downtotal"] ); } } return $ary; } /** * Function to load the settings for all transfers. returns ref to array * * @return array-ref */ function &loadAllTransferSettings() { global $db; $recordset = $db->Execute("SELECT * FROM tf_transfers"); $ary = array(); while ($row = $recordset->FetchRow()) { $ary[$row["transfer"]] = array( "type" => $row["type"], "client" => $row["client"], "hash" => $row["hash"], "datapath" => $row["datapath"], "savepath" => $row["savepath"], "running" => $row["running"], "max_upload_rate" => $row["rate"], "max_download_rate" => $row["drate"], "die_when_done" => $row["runtime"], "max_uploads" => $row["maxuploads"], "superseeder" => $row["superseeder"], "minport" => $row["minport"], "maxport" => $row["maxport"], "sharekill" => $row["sharekill"], "maxcons" => $row["maxcons"], "rerequest" => $row["rerequest"] ); } return $ary; } /** * initGlobalTransfersArray */ function initGlobalTransfersArray() { global $transfers; // transfers $transfers = array(); // settings $transferSettings =& loadAllTransferSettings(); $transfers['settings'] = $transferSettings; // totals $transferTotals =& loadAllTransferTotals(); $transfers['totals'] = $transferTotals; // sum $transfers['sum'] = array( 'maxcons' => getSumMaxCons(), 'rate' => getSumMaxUpRate(), 'drate' => getSumMaxDownRate() ); // owner $transferOwner =& loadAllTransferOwner(); $transfers['owner'] = $transferOwner; } /** * injects a transfer * * @param $transfer * @return boolean */ function injectTransfer($transfer) { global $cfg; $sf = new StatFile($transfer); $sf->running = "2"; // file is new $sf->size = getTransferSize($transfer); if ($sf->write()) { // set transfers-cache cacheTransfersSet(); return true; } else { AuditAction($cfg["constants"]["error"], "stat-file cannot be written when injecting : ".$transfer); return false; } } /** * get Owner * * @param $transfer * @return string */ function getOwner($transfer) { global $cfg, $db, $transfers; if (isset($transfers['owner'][$transfer])) { return $transfers['owner'][$transfer]; } else { // Check log to see what user has a history with this file $transfers['owner'][$transfer] = $db->GetOne("SELECT user_id FROM tf_log WHERE file=".$db->qstr($transfer)." AND (action=".$db->qstr($cfg["constants"]["file_upload"])." OR action=".$db->qstr($cfg["constants"]["url_upload"])." OR action=".$db->qstr($cfg["constants"]["reset_owner"]).") ORDER BY time DESC"); return ($transfers['owner'][$transfer] != "") ? $transfers['owner'][$transfer] : resetOwner($transfer); // try and get the owner from the stat file; } } /** * reset Owner * * @param $transfer * @return string */ function resetOwner($transfer) { global $cfg, $db, $transfers; // log entry has expired so we must renew it $rtnValue = "n/a"; if (file_exists($cfg["transfer_file_path"].$transfer.".stat")) { $sf = new StatFile($transfer); $rtnValue = (IsUser($sf->transferowner)) ? $sf->transferowner /* We have an owner */ : GetSuperAdmin(); /* no owner found, so the super admin will now own it */ // add entry to the log $sql = "INSERT INTO tf_log (user_id,file,action,ip,ip_resolved,user_agent,time)" ." VALUES (" . $db->qstr($rtnValue)."," . $db->qstr($transfer)."," . $db->qstr($cfg["constants"]["reset_owner"])."," . $db->qstr($cfg['ip'])."," . $db->qstr($cfg['ip_resolved'])."," . $db->qstr($cfg['user_agent'])."," . $db->qstr(time()) .")"; $result = $db->Execute($sql); if ($db->ErrorNo() != 0) dbError($sql); } $transfers['owner'][$transfer] = $rtnValue; return $rtnValue; } /** * IsOwner * * @param $user * @param $owner * @return boolean */ function IsOwner($user, $owner) { return (($user) == ($owner)); } ?>