<?

define('READ_FROM_CACHE_RESET', 
"Перед продолжением работы ПЕРЕЗАГРУЗИТЕ КОМПЬЮТЕР.
Иначе скорость чтения будет определяться неправильно.
Объем тестируемого пространства меньше оперативной памяти,
поэтому нужна перезагрузка (это связано с файловым кешем)."
);


class Ui_read_blocks {

	static $autorun = false; // если стоит true, то этап автоматически запускается. Устанавливается Ui_create_blocks

	// действия при активации этапа
	static function active() {
		GLOBAL $INFO, $setting, $Paths, $GOP, $OP, $Graphs, $Bt_run, $Disc_info, $log;

		// Когда запись файлов остановилось для пересчета, и выполнила эту функцию. Но так как она пишет во внешнее INFO, то данные о размере пользовательских файлов, перезатерлись. 
		//Stat::calc_stat_userfiles();
		// заблокировал чтобы график не менялся если на диске произошли какие то изменения.

		// засунем информацию о диске в info. Здесь потому что корретно отработает пересчет пользовательских файлов
		$INFO['disk_size'] = $Disc_info->size($Paths->disc_name, 'GB');
		$INFO['disk_letter'] = $Paths->disc_name;
		$INFO['disks_in_system'] = $Disc_info->get_all();

		// надо прописывать во всех этапах!
		Step_activator::graphs_enabled(1);

		$Graphs['disk']->legend->visible(GRD_good_write, 0);
		$Graphs['disk']->legend->visible(GRD_slow_auto, 1);
		$Graphs['disk']->legend->visible(GRD_read_err, 1);
		$Graphs['disk']->legend->visible(GRD_create_err, 1);
		$Graphs['disk']->legend->visible(GRD_frag, 1);
		$Graphs['disk']->legend->visible(GRD_all_slow, 1);
		$Graphs['disk']->legend->visible(GRD_result_space, 1);


		// сбрасываем ползунки на значения по умолчанию
		// вдруг в предыдщий раз они были задраны слишком. А так как сейчас ползуки блокируются, человек может подумать что все плохо с диском
		$setting->set_to_def('analize_mode');
		$setting->set_to_def('min_frag_size');
		$setting->set_to_def('analize_good_speed');

		// поскольку мы должны руками его очищать. Он конечно при запуске потока очистится, но до этого момента будет не красиво.
		if(!$INFO['recovery_fname']) {
			//rint "очищаем read_blocks_fast";
			$INFO['read_blocks_fast'] = 0; // если не очистить, в графике диска будет показывать итоговое пространство, хотя чтение еще не начинали
		}

		// запускаем процесс
		// TODO: если только не была нажата кнопка "повторить"

		if(self::$autorun and $OP['autorun_steps']) {
			self::$autorun = false;
			$INFO['autorun_over_create'] = true;
			$Bt_run->onClick('read_blocks');
		}
	}


	// вызывается так же на этапе создания, чтобы посреди обработки программа не остановилась
	static function check_setting() {
		GLOBAL $log, $GOP, $OP, $Ui_fields, $Lang, $Graphs, $Disc_info, $Analize_autochoice;

		// проверяем чтобы скорости были установленны правильно
		$good = $Ui_fields['good_speed'];
		$antifrag = $Ui_fields['antifrag_speed'];
		$sect = $Ui_fields['sect_speed'];
		
		// проверить чтобы ни одной из скоростей не была нулевой
		$fields = array($good, $antifrag, $sect);
		foreach($fields as $field) {
			if($field->get() <= 0) {
				messageDlg($field->title . ' ' . NOT_BE_ZERO, mtInformation, MB_OK);
				return false;
			}
		}

		$error  = '';
		// базовая скорость не может быть выше максимальной скорости подбора
		$max_speed = $Analize_autochoice->get_podbor_max_speed();
		list($floor, $ceil, $near) = $Graphs['speed']->near_cols($max_speed);
		if($good->get() > $floor ) {
			$error .= "$good->title не может быть больше  $floor MB. \n\n";
			$good->set($floor);
		}

		if($good->get() < $antifrag->get()) {
			$error .=  "$antifrag->title " . NOT_BE_OVER . " {$good->title}. \n\n";
			$antifrag->set($good->get());
		}

		if($antifrag->get() < $sect->get()) {
			$error .= "$sect->title " . NOT_BE_OVER . " {$antifrag->title}. \n\n";
			$sect->set($antifrag->get());
		}

		if($error) {
			$text = $error . "Программа подкорректировала неправильные настройки.";
			messageDlg($text, mtInformation, MB_OK);
			return false;
		}	 

		return true;
	}

	static function before_run() {
		GLOBAL $INFO, $log, $GOP, $OP, $Ui_fields, $Lang, $Graphs, $Disc_info;

		if(!self::check_setting())
			return false;

		// на всякий случай проверяем настройки при каждом запуске, ведь человек может их изменить
		if(!empty($INFO['recovery_fname'])) {
			return true;
		}	

		// обнуляем в графике диска тестовые файлы и скрываем поле в легенде
		$Graphs['disk']->set_col(GRD_good_write, 0);
		$Graphs['disk']->legend->visible(GRD_good_write, 0);
		
		// если отлючать кеширование, надо запись тоже делать не кешируемой. В текущем виде она выборочно влияет на скорость чтения хотя там четко прописано что никакого кеширования
		// проверяем, можно ли запускать чтение или надо сбрасывать кеш перезапуском винды
		$need_restart = true;
		// если комп уже перезагружен после записи
		if($GOP['prog_load_time'] > $INFO['create_blocks_stop_time']) {
			$need_restart = false;
			//$log->line("Кеш сброшен перезагрузкой компьютера");
		}
		else {
			// если объем тестируемого пространства >= оперативки, все ок
			$ramKb = TotalPhysicalMemoryMB() * 1024;
			if($ramKb and $Disc_info->testing_size  >= $ramKb) {
				$need_restart = false;
				//$log->line("Кеш сброшен переполнением памяти: ");
			}
		}

		// выводим окно что надо перезапустить
		if($need_restart and !$OP['blocking_dialog']) {
			messageDlg(READ_FROM_CACHE_RESET, mtWarning, MB_OK);
			return false;
		}

		return true;
	}

	static function after_run_complete() {
		GLOBAL $INFO, $log;

		Ui_analize_blocks::$autorun = true;
	}

	// перезапускаем поток с включенным режимом "пропуск файлов на которых зависли"
	// может запускаться как по кнопке пользователем, так и автоматически при определении зависания
	static function restart_and_skip_files($mode) {
		GLOBAL $INFO, $OP, $Ui_thread, $Bt_run, $setting, $Paths;

		if($mode == 'all') {
			$text ="Уверены что хотите пропустить все оставшиеся сектора и завершить этап?\n Они будут заблокированы.";
			$res = messageDlg($text, mtWarning, MB_OKCANCEL);
			if($res == 2)
				return false;

			$skip_mb = 10*1024*1024; // в потоке программа возьмет сколько надо
		}
		else {
			if($mode == 'hand') 
				 $name = 'hand_skip_size';
			else $name =  'zavis_skip_size';

			$skip_mb = c('Fm->'.$name)->text;
		}

		$num_skip = ceil(($skip_mb*1024) / $OP['block_size']);
		if($num_skip <= 0) {
			messageDlg("Нельзя пропустить секторов меньше, чем $OP[block_size] kb", mtInformation, MB_OK);
			return false;
		}

		$start = $Ui_thread->get_protect('cur_fname');

		if($Ui_thread->check_run()) {
			$Bt_run->stop($INFO['step']);
			sleep(1);
		}

		// для ручного режима пропускаем на один файл меньше. Потому что по умолчанию 
		if($mode == 'hand') 
			$num_skip --; // да, он может быть нулем, тогда будет пропущен один файл

		$to_info = array(
			'mode_skip_start'=>$start,
			'mode_skip_finish'=>$start + $num_skip,
			'mode_skip'=> true,
		);
		$INFO = array_merge($INFO, $to_info);
		$setting->edit_recovery_info_if_exist($to_info);

		$Bt_run->start($INFO['step']);

		// $OP['mode_skip'] = false;
		// $OP['mode_skip_start'] = -1;
		// $OP['mode_skip_finish'] = -1;
	}
}


?>