<?php
$excepttables = array_merge(array($tablepre.'adminsessions', $tablepre.'failedlogins', $tablepre.'pmsearchindex', $tablepre.'relatedthreads', $tablepre.'rsscaches', $tablepre.'searchindex', $tablepre.'spacecaches', $tablepre.'sessions'),
	($supe['status'] ? array($supe['tablepre'].'cache', $supe['tablepre'].'corpus', $supe['tablepre'].'rss', $supe['tablepre'].'spacecache', $supe['tablepre'].'tagcache') : array()));

if(!$backupdir = $db->result($db->query("SELECT value FROM {$tablepre}settings WHERE variable='backupdir'"), 0)) {
	$backupdir = random(6);
	@mkdir(MODEPATH.'./cache/backup_'.$backupdir, 0777);
	$db->query("REPLACE INTO {$tablepre}settings (variable, value) values ('backupdir', '$backupdir')");
}
$backupdir = 'backup_'.$backupdir;
if(!is_dir(MODEPATH.'./cache/'.$backupdir)) {
	mkdir(MODEPATH.'./cache/'.$backupdir, 0777);
}

if($menu == 'export') {
	if(cpchecksubmit('export',1)) {
		$db->query('SET SQL_QUOTE_SHOW_CREATE=0', 'SILENT');
		if(!$exportdbname || preg_match("/(\.)(exe|jsp|asp|aspx|cgi|fcgi|pl)(\.|$)/i", $exportdbname)) {
			cpmsg('db_export_filename_unaccepted');
		}	
		$backuptime = gmdate("$dateformat $timeformat", $time + $timeoffset * 3600);	
		$tables = arraykeys2(getables($tablepre), 'Name');	
		$volume = intval($volume) + 1;
		$idstring = '# backupinfo: '.base64_encode("$time,Swoter,$volume")."\n";
		$dumpcharset = str_replace('-', '', $GLOBALS['charset']);
		if($db->version() > '4.1') {
			if($dbformat == 'MYSQL40') {
				$db->query("SET SQL_MODE='MYSQL40'");
			} elseif($dbformat == 'MYSQL41') {
				$db->query("SET SQL_MODE=''");
			}
		}

		$backupfilename = MODEPATH.'./cache/'.$backupdir.'/'.str_replace(array('/', '\\', '.'), '', $exportdbname);
		$sqldump = '';
		$tableid = intval($tableid);
		$startfrom = intval($startfrom);
		$complete = TRUE;				
		for(; $complete && $tableid < count($tables) && strlen($sqldump) + 500 < $dbcut * 1000; $tableid++) {
			$sqldump .= sqldumptable($tables[$tableid], $startfrom, strlen($sqldump));
			if($complete) {
				$startfrom = 0;
			}
		}
		$dumpfile = $backupfilename."_%s".'.sql';

		!$complete && $tableid--;
		if(trim($sqldump)) {
			$sqldump = "$idstring".
				"# <?exit();?>\n".
				"# Multi-Volume Data Dump Vol.$volume\n".
				"# Time: $time\n".
				"# Type: $backuptime\n".
				"# Table Prefix: $tablepre\n".
				"#\n".$sqldump;
			$dumpfilename = sprintf($dumpfile, $volume);
			@$fp = fopen($dumpfilename, 'wb');
			@flock($fp, 2);
			if(@!fwrite($fp, $sqldump)) {
				@fclose($fp);
				cpmsg('db_export_file_invalid');
			} else {
				fclose($fp);
				if($usezip == 2) {
					$fp = fopen($dumpfilename, "r");
					$content = @fread($fp, filesize($dumpfilename));
					fclose($fp);
					$zip = new zipfile();
					$zip->addFile($content, basename($dumpfilename));
					$fp = fopen(sprintf($backupfilename."-%s".'.zip', $volume), 'w');
					if(@fwrite($fp, $zip->file()) !== FALSE) {
						@unlink($dumpfilename);
					}
					fclose($fp);
				}
				unset($sqldump, $zip, $content);
				cpmsg('db_export_multivol_redirect', "index.php?action=db&menu=export&exportdbname=".rawurlencode($exportdbname)."&method=multivol&dbcut=".rawurlencode($dbcut)."&volume=".rawurlencode($volume)."&tableid=".rawurlencode($tableid)."&startfrom=".rawurlencode($startrow)."&extended=".rawurlencode($extended)."&sqlcharset=".rawurlencode($sqlcharset)."&dbformat=".rawurlencode($dbformat)."&export=yes&dbtextype=$dbtextype&dbzip=$dbzip");
			}	
		}else{
			$volume--;
		$filelist = '<ul>';
			if($dbzip) {
				require_once MODEPATH.'./'.$adminpath.'/zip.class.php';
				$zip = new zipfile();
				$zipfilename = $backupfilename.'.zip';
				$unlinks = '';
				for($i = 1; $i <= $volume; $i++) {
					$filename = sprintf($dumpfile, $i);
					$content = readfromfile($filename);
					$zip->addFile($content, basename($filename));
					$unlinks .= "@unlink('$filename');";
					$filelist .= "<li><a href=\"".$backupdir.'/'.basename($filename)."\">$filename\n";
				}		
				
				if(writetofile($zipfilename,$zip->file())) {
					eval($unlinks);
				}else{
					cpmsg('db_export_multivol_succeed');
				}	
				unset($sqldump, $zip, $content);			
				@touch(MODEPATH.'./cache/'.$backupdir.'/index.htm');
				$filename = "/cache/".$backupdir.'/'.basename($zipfilename);
				cpmsg('db_export_zip_succeed');

			}else{
				@touch(MODEPATH.'./cache/'.$backupdir.'/index.htm');
				for($i = 1; $i <= $volume; $i++) {
					$filename = sprintf($dumpfile, $i);
					$filelist .= "<li><a href=\"/cache/".$backupdir.'/'.basename($filename)."\">$filename</a>\n";
				}
				cpmsg('db_export_multivol_succeed');		
			}
		
		}
	}else{
		$tables = getables($tablepre);
		$exportdbname = gmdate("Ymd",$time + $timeoffset * 3600).'_'.random(5);
		@include lang('themes','themes/admin');
		include theme('db_export','themes/admin','admin');
	}
}elseif($menu == 'import'){
	if(cpchecksubmit('import',1)) {
		$file = MODEPATH.'./cache/'.$backupdir.'/'.$filename;
		if(!file_exists($file)) {
			cpmsg('db_import_file_illegal');
		}
		if($import == 'zip') {
			require_once MODEPATH.'./'.$adminpath.'/zip.class.php';
			$unzip = new SimpleUnzip();	

			$unzip->ReadFile($file);

			if($unzip->Count() == 0 || $unzip->GetError(0) != 0 || !preg_match("/\.sql$/i", $importfile = $unzip->GetName(0))) {
				cpmsg('db_import_file_illegal');
			}

			$identify = explode(',', base64_decode(preg_replace("/^# backupinfo:\s*(\w+).*/s", "\\1", substr($unzip->GetData(0), 0, 256))));
			if($identify[1] != 'Swoter') {
				cpmsg('db_import_file_illegal');
			}

			$sqlfilecount = 0;
			$filename = '';
			foreach($unzip->Entries as $entry) {
				if(preg_match("/\.sql$/i", $entry->Name)) {
					if($sqlfilecount) {
						$filename = $entry->Name;
					}
					writetofile(MODEPATH.'./cache/'.$backupdir.'/'.$entry->Name,$entry->Data);			
					$sqlfilecount++;
				}
			}
			if(!$sqlfilecount) {
				cpmsg('db_import_file_illegal');
			}			
			$datafile_next = preg_replace("/_([0-9_])+(\..+)$/", "_1\\2", $filename);	
			if(file_exists(MODEPATH.'./cache/'.$backupdir.'/'.$datafile_next)) {
				cpmsg('db_import_unzip_go','index.php?action=db&menu=import&import=sql&gonext=yes&filename='.$datafile_next,'NOPERM');
			}else{
				cpmsg('db_import_unzip','index.php?action=db&menu=import');
			}
			
		}elseif($import == 'sql'){
			$sqls = readfromfile($file);
			if(!$sqls) {
				cpmsg('db_import_file_illegal');
			}
			$identify = explode(',', base64_decode(preg_replace("/^# backupinfo:\s*(\w+).*/s", "\\1", substr($sqls, 0, 256))));
			$sqlquery = splitsql($sqls);
			unset($sqls);

			foreach($sqlquery as $sql) {

				$sql = syntablestruct(trim($sql), $db->version() > '4.1', $dbcharset);
				
				if(substr($sql, 0, 11) == 'INSERT INTO') {
					$sqldbname = substr($sql, 12, 20);
					$dotpos = strpos($sqldbname, '.');
					if($dotpos !== FALSE) {
						if(empty($supe['dbmode'])) {
							$sql = 'INSERT INTO `'.$supe['dbname'].'`.'.substr($sql, 13 + $dotpos);
						} else {
							supe_dbconnect();
						}
					}
				}

				if($sql != '') {
					$db->query($sql, 'SILENT');
					if(($sqlerror = $db->error()) && $db->errno() != 1062) {
						$db->errorreport('MySQL Query Error', $sql);
					}
				}
			}
			$datafile_next = preg_replace("/_($identify[2])(\..+)$/", "_".($identify['2'] + 1)."\\2", $filename);			
			if($identify[2] == 1 && !$gonext) {
				if(file_exists(MODEPATH.'./cache/'.$backupdir.'/'.$datafile_next)) {
					cpmsg('db_import_multivol_prompt','index.php?action=db&menu=import&import=sql&gonext=yes&filename='.$datafile_next,'NOPERM');
				}else{
					cpmsg('db_import_succeed');
				}
			}else{
				if($gonext && file_exists(MODEPATH.'./cache/'.$backupdir.'/'.$datafile_next)) {
					cpmsg('db_import_multivol_redirect','index.php?action=db&menu=import&import=sql&gonext=yes&filename='.$datafile_next);
				}else{
					cpmsg('db_import_succeed');
				}
			}
		}
	}elseif(cpchecksubmit('updatelist')){
		if(is_array($delete)) {
			foreach($delete AS $key => $sql) {
				@unlink(MODEPATH.'./cache/'.$backupdir.'/'.$delete[$key]);
			}

		}
		cpmsg('succeeded','index.php?action=db&menu=import');
	}else{
		$exportlog = array();
		//$time,$exportset,$volume
		if(is_dir(MODEPATH.'./cache/'.$backupdir)) {
		
			$dir = dir(MODEPATH.'./cache/'.$backupdir);
			while($entry = $dir->read()) {
				$filedir = MODEPATH.'./cache/'.$backupdir.'/'.$entry;
				
				if(is_file($filedir)) {
					if(preg_match("/\.sql$/i", $entry)) {
				
						$filesize = filesize($filedir);
						$fp = fopen($filedir, 'rb');
						$identify = explode(',', base64_decode(preg_replace("/^# backupinfo:\s*(\w+).*/s", "\\1", fgets($fp, 256))));
						fclose ($fp);
						$exportlog[] = array(
							'exportset' => $identify[2],
							'volume' => $identify[3],
							'filename' => $entry,
							'type' => 'sql',
							'filedir' => $filedir,
							'dateline' => gmdate("$dateformat $timeformat", filemtime($filedir)+ $timeoffset * 3600),
							'size' => sizecount($filesize),
						);
					} elseif(preg_match("/\.zip$/i", $entry)) {
						$filesize = filesize($filedir);
						$exportlog[] = array(
							'type' => 'zip',
							'filename' => $entry,
							'filedir' => $filedir,
							'size' => sizecount($filesize),
							'dateline' => gmdate("$dateformat $timeformat", filemtime($filedir)+ $timeoffset * 3600),
						);
					}
				}
			}
			$dir->close();
		} else {
			cpmsg('db_export_dest_invalid');
		}
		@sort($exportlog);
		include theme('db_import','themes/admin','admin');
	}
}else{


}

function getables($tablepre = '') {
	global $db;
	$arr = explode('.', $tablepre);
	$dbname = $arr[1] ? $arr[0] : '';
	$sqladd = $dbname ? " FROM $dbname LIKE '$arr[1]%'" : "LIKE '$tablepre%'";
	!$tablepre && $tablepre = '*';
	$tables = $table = array();
	$query = $db->query("SHOW TABLE STATUS $sqladd");
	while($table = $db->fetch_array($query)) {
		$table['Name'] = ($dbname ? "$dbname." : '').$table['Name'];
		$tables[] = $table;
	}
	return $tables;
}
function arraykeys2($array, $key2) {
	$return = array();
	foreach($array as $val) {
		$return[] = $val[$key2];
	}
	return $return;
}

function syntablestruct($sql, $version, $dbcharset) {

	if(strpos(trim(substr($sql, 0, 18)), 'CREATE TABLE') === FALSE) {
		return $sql;
	}

	$sqlversion = strpos($sql, 'ENGINE=') === FALSE ? FALSE : TRUE;

	if($sqlversion === $version) {

		return $sqlversion && $dbcharset ? preg_replace(array('/ character set \w+/i', '/ collate \w+/i', "/DEFAULT CHARSET=\w+/is"), array('', '', "DEFAULT CHARSET=$dbcharset"), $sql) : $sql;
	}

	if($version) {
		return preg_replace(array('/TYPE=HEAP/i', '/TYPE=(\w+)/is'), array("ENGINE=MEMORY DEFAULT CHARSET=$dbcharset", "ENGINE=\\1 DEFAULT CHARSET=$dbcharset"), $sql);

	} else {
		return preg_replace(array('/character set \w+/i', '/collate \w+/i', '/ENGINE=MEMORY/i', '/\s*DEFAULT CHARSET=\w+/is', '/\s*COLLATE=\w+/is', '/ENGINE=(\w+)(.*)/is'), array('', '', 'ENGINE=HEAP', '', '', 'TYPE=\\1\\2'), $sql);
	}
}
?>