Files
libTononix/KernelManagement.class.php
2021-07-22 04:05:11 -04:00

241 lines
8.4 KiB
PHP

<?php
namespace libTononix;
require_once("vendor/autoload.php");
use Noodlehaus\Config;
use \Noodlehaus\Parser\Json;
use \Noodlehaus\Parser\Properties;
use \Noodlehaus\Parser\Xml;
class KernelManagement
{
protected $cKernelVersion;
protected $cKernelName;
protected $cKernelFeatures;
protected $cKernelBinary;
protected $cKernelHash;
private $cBootPath;
private $aInstalledKernels;
private $oConfiguration;
private $cPrefixPath;
private $aPartitionInfo;
private $aBootConfiguration;
private $abootimg;
function __construct()
{
if(!defined("IN_PREFIX"))
{
$this->cBootPath = "/boot";
} else {
if(!getenv("EPREFIX"))
{
// We're gonna assume the directory, we seem to be inside a prefix but the EPREFIX variable is missing.
$this->cBootPath = "/home/phablet/.local/system/boot";
$this->cPrefixPath = "/home/phablet/.local/system";
} else {
$this->cBootPath = getenv("EPREFIX") . "/boot";
$this->cPrefixPath = getenv("EPREFIX");
}
}
// Genkernel is nice enough to make a symlink to the last compiled kernel, so we'll use that.
$this->cKernelBinary = realpath($this->cBootPath."/kernel");
$this->cKernelHash = md5(file_get_contents($this->cKernelBinary));
$this->loadConfiguration();
if(!$this->aInstalledKernels)
{
// TODO: Replace this with an actual error code indicating the configuration file is not set up.
$this->doLibraryFirstInit();
}
}
private function saveConfiguration()
{
$this->oConfiguration->set("device.installed-kernels", json_encode($this->aInstalledKernels));
$this->oConfiguration->set("device.info.partitions", $this->aPartitionInfo);
$this->oConfiguration->set("device.boot.configuration", $this->aBootConfiguration);
$this->oConfiguration->toFile($this->cPrefixPath."/etc/tononixOS/kernel.conf", new \Noodlehaus\Writer\Xml());
}
private function installKernel($kernelVersion = "3.4.0107", $kernelPath = null)
{
if(!$kernelPath)
{
$kernelPath = realpath($this->cPrefixPath."/boot/kernel");
}
// TODO: Finish Function
}
private function loadConfiguration()
{
$this->oConfiguration = null;
$this->aInstalledKernels = null;
$this->aPartitionInfo = null;
$this->aBootConfiguration = null;
$this->oConfiguration = new Config($this->cPrefixPath."/etc/tononixOS/kernel.conf", New Xml);
$this->aInstalledKernels = json_decode($this->oConfiguration->get("device.installed-kernels"));
$this->aPartitionInfo = $this->oConfiguration->get("device.info.partitions");
$this->aBootConfiguration = $this->oConfiguration->get("device.boot.configuration");
}
public function getPartitionNode($sPartitionNode)
{
if(key_exists($sPartitionNode, $this->aPartitionInfo))
{
return $this->aPartitionInfo[$sPartitionNode];
}
}
public function retrieveCurrentInstalledBootImage($storePath = null)
{
if(!$storePath)
{
$storePath = $this->cPrefixPath."/boot/old_boot.img";
}
if(!$this->aPartitionInfo)
{
$this->detectPartitionLayout();
}
exec("dd if=".$this->aPartitionInfo['kernel']." of=".$storePath);
}
// Pulls currently installed boot image from the defined boot partition, then extracts it with abootimg.
public function extractCurrentInstalledBootImage()
{
if(!`which abootimg`)
{
return false;
}
$this->retrieveCurrentInstalledBootImage();
$pwd = getcwd();
chdir($this->cPrefixPath."/boot");
exec("abootimg -x old_boot.img");
chdir($pwd);
}
private function __getBootSlot()
{
// This will allow us to know what boot slot we're supposed to be flashing into, perhaps we can make a treble compatible system updater with this?
$bootSlot = trim(`getprop ro.boot.slot_suffix`);
if(empty($bootSlot))
{
$bootSlot = "";
}
return $bootSlot;
}
public function installKernelTree($branch = 'flo', $repository = "https://tonoxisisle.services/git/tononixOS/ubports_kernel_google_msm", $kernelName = "3.4.y-tononixOS")
{
$git = new CzProject\GitPhp\Git;
$repo = $git->cloneRepository($repository, $_ENV['HOME']."/.local/system/usr/src/".$kernelName);
if(!empty($branch))
{
$repo->checkout($branch);
}
$repo->pull();
$cwd = getcwd();
chdir($_ENV['HOME']."/.local/system/usr/src/".$kernelName);
$kVersion = shell_exec("make kernelversion");
if(empty($kVersion)) {
$versionArray = explode("-", $kernelName);
$kVersion = $versionArray[0];
}
// Until we implement the Kernel Features detection, we're going to null it out for the NYI string
$this->addInstalledKernel($kVersion, $_ENV['HOME']."/.local/system/usr/src/".$kernelName, null, $kernelName);
}
public function removeKernelTree($kernelName)
{
}
public function buildKernel($kernelName)
{
}
public function detectBootConfiguration()
{
if(!file_exists($this->cPrefixPath."/boot/old_boot.img"))
{
$this->extractCurrentInstalledBootImage();
}
$aboot = new Config($this->cPrefixPath."/boot/bootimg.cfg", new Properties);
$this->aBootConfiguration = array();
$this->aBootConfiguration['bootsize'] = $aboot->get("bootsize");
$this->aBootConfiguration['pagesize'] = $aboot->get("pagesize");
$this->aBootConfiguration['kerneladdr'] = $aboot->get("kerneladdr");
$this->aBootConfiguration['ramdiskaddr'] = $aboot->get("ramdiskaddr");
$this->aBootConfiguration['secondaddr'] = $aboot->get("secondaddr");
$this->aBootConfiguration['tagsaddr'] = $aboot->get("tagsaddr");
$this->aBootConfiguration['cmdline'] = $aboot->get("cmdline");
$bootSlot = $this->__getBootSlot();
if(!empty($bootSlot)) $this->aBootConfiguration['bootslot'] = $bootSlot;
$this->saveConfiguration();
}
function detectPartitionLayout()
{
$partitionLayout = array();
if(!is_dir("/dev/disk"))
{
return false;
}
$partitionLayout['system'] = realpath("/dev/disk/by-partlabel/system");
$partitionLayout['cache'] = realpath("/dev/disk/by-partlabel/cache");
$partitionLayout['userdata'] = realpath("/dev/disk/by-partlabel/userdata");
$partitionLayout['bootloader'] = realpath("/dev/disk/by-partlabel/aboot");
$partitionLayout['bootloaderb'] = realpath("/dev/disk/by-partlabel/abootb");
$partitionLayout['baseband'] = realpath("/dev/disk/by-partlabel/radio");
$partitionLayout['recovery'] = realpath("/dev/disk/by-partlabel/recovery");
$partitionLayout['kernel'] = realpath("/dev/disk/by-partlabel/boot");
$partitionLayout['modemst1'] = realpath("/dev/disk/by-partlabel/modemst1");
$partitionLayout['modemst2'] = realpath("/dev/disk/by-partlabel/modemst2");
$this->aPartitionInfo = $partitionLayout;
$this->saveConfiguration();
}
private function addInstalledKernel($version, $path, $aFeaturesList = "NYI", $sKernelName = null)
{
$this->aInstalledKernels[] = array("path" => "$path",
"version" => "$version",
"features" => $aFeaturesList,
"name" => "$sKernelName");
return;
}
private function delInstalledKernel($version)
{
}
function doLibraryFirstInit()
{
if(file_exists($this->cPrefixPath."/boot/kernel"))
{
// We already have an installed kernel, let's record it as our first installed kernel in the array.
$this->addInstalledKernel("0.0.0-stock", realpath($this->cPrefixPath."/boot/kernel"));
}
$this->detectPartitionLayout();
$this->detectBootConfiguration();
$this->saveConfiguration();
$this->loadConfiguration();
return true;
}
}