--debug to trigger logging verbosity

- Logging verbosity triggered by `--debug` command-line option.
- Implemented callback function for libalpm's logging callback.
- Increased TransactionFlags to 16 bits from 8 bits to accomodate the
  bitlength required for additional transaction flags.
This commit is contained in:
Xavier Moffett 2024-09-11 22:04:22 -04:00
parent 024bab1d7f
commit 2819f5d216
Signed by: Sapphirus
GPG key ID: A6C061B2CEA1A7AC
12 changed files with 76 additions and 50 deletions

View file

@ -73,8 +73,10 @@ pub fn transact() -> Result<()> {
let config: Global = deserialize(&mut file)?;
let alpm_remotes: AlpmConfigData = deserialize(&mut file)?;
let mut metadata: TransactionMetadata = deserialize(&mut file)?;
let alpm = sync::instantiate_alpm_agent(&config, &alpm_remotes);
let mut handle = TransactionHandle::new(&mut metadata).alpm_handle(alpm).config(&config).agent();
let handle = TransactionHandle::new(&mut metadata);
let (transflags, ..) = handle.metadata().retrieve_flags();
let alpm = sync::instantiate_alpm_agent(&config, &alpm_remotes, &transflags.expect("TransactionFlags"));
let mut handle = handle.alpm_handle(alpm).config(&config).agent();
if let Err(err) = conduct_transaction(&config, &mut handle, params) {
handle.release();

View file

@ -63,6 +63,7 @@ macro_rules! to_static_str {
}
lazy_static! {
pub static ref VERBOSE: bool = var("PACWRAP_VERBOSE").is_ok_and(|v| v == "1");
pub static ref UID: u32 = geteuid().as_raw();
pub static ref GID: u32 = getegid().as_raw();
pub static ref HOME: &'static str = env("HOME");

View file

@ -262,7 +262,12 @@ pub fn transaction_agent(ins: &ContainerHandle, params: TransactionParameters, m
}
pub fn pacwrap_key(cmd: Vec<&str>) -> Result<()> {
match Command::new(PACMAN_KEY_SCRIPT).stderr(Stdio::null()).args(cmd).spawn() {
match Command::new(PACMAN_KEY_SCRIPT)
.stderr(Stdio::null())
.env("COLOURTERM", *COLORTERM)
.args(cmd)
.spawn()
{
Ok(proc) => wait_on_process(PACMAN_KEY_SCRIPT, proc),
Err(error) => err!(ErrorKind::ProcessInitFailure(PACMAN_KEY_SCRIPT, error.kind()))?,
}

View file

@ -22,32 +22,25 @@ use std::{
os::unix::fs::symlink,
path::Path,
process::exit,
time::{SystemTime, UNIX_EPOCH},
};
use alpm::{Alpm, SigLevel, Usage};
use alpm::{Alpm, LogLevel, SigLevel, Usage};
use lazy_static::lazy_static;
use pacmanconf::{self, Config, Repository};
use serde::{Deserialize, Serialize};
use crate::{
config::{
cache::ContainerCache,
global::ProgressKind,
ContainerHandle,
ContainerType::*,
ContainerVariables,
Global,
CONFIG,
},
constants::{ARROW_RED, BAR_GREEN, BOLD, CACHE_DIR, CONFIG_DIR, DATA_DIR, RESET},
config::{global::ProgressKind, ContainerHandle, ContainerType::*, ContainerVariables, Global, CONFIG},
constants::{ARROW_RED, BAR_GREEN, BOLD, CACHE_DIR, CONFIG_DIR, DATA_DIR, RESET, UNIX_TIMESTAMP, VERBOSE},
err,
error,
exec::pacwrap_key,
impl_error,
lock::Lock,
sync::{
event::download::{self, DownloadEvent},
filesystem::create_hard_link,
filesystem::{create_blank_state, create_hard_link},
transaction::{TransactionAggregator, TransactionFlags},
},
Error,
ErrorGeneric,
@ -55,8 +48,6 @@ use crate::{
Result,
};
use self::filesystem::create_blank_state;
pub mod event;
pub mod filesystem;
pub mod schema;
@ -123,7 +114,7 @@ impl Display for SyncError {
Self::NothingToDo => write!(fmter, "Nothing to do."),
_ => Ok(()),
}?;
if let Self::TransactionFailure(_) = self {
Ok(())
} else if let Self::SignalInterrupt = self {
@ -192,9 +183,26 @@ impl AlpmConfigData {
}
}
pub fn instantiate_alpm_agent(config: &Global, remotes: &AlpmConfigData) -> Alpm {
fn alpm_log_callback(level: LogLevel, msg: &str, counter: &mut usize) {
let now = SystemTime::now().duration_since(UNIX_EPOCH).unwrap();
let time = now.as_secs() as usize - *counter;
let nano = now.subsec_nanos().to_string();
let log_level = level.bits() / 4;
let verbosity = if *VERBOSE { 3 } else { 2 };
if log_level < verbosity {
eprint!("[{}.{:.6}] [ALPM] {}", time, nano, msg);
}
}
pub fn instantiate_alpm_agent(config: &Global, remotes: &AlpmConfigData, transflags: &TransactionFlags) -> Alpm {
let mut handle = Alpm::new("/mnt/fs", "/mnt/fs/var/lib/pacman/").unwrap();
let hook_dirs = vec!["/mnt/fs/usr/share/libalpm/hooks/", "/mnt/fs/etc/pacman.d/hooks/"];
let debug = transflags.intersects(TransactionFlags::DEBUG);
if debug {
handle.set_log_cb(*UNIX_TIMESTAMP as usize, alpm_log_callback);
}
handle.set_disable_sandbox(config.alpm().disable_sandbox());
handle.set_logfile("/mnt/share/pacwrap.log").unwrap();
@ -209,12 +217,17 @@ pub fn instantiate_alpm_agent(config: &Global, remotes: &AlpmConfigData) -> Alpm
handle
}
pub fn instantiate_alpm(inshandle: &ContainerHandle) -> Alpm {
alpm_handle(inshandle.vars(), format!("{}/var/lib/pacman/", inshandle.vars().root()), &*DEFAULT_ALPM_CONF)
pub fn instantiate_alpm(inshandle: &ContainerHandle, transflags: &TransactionFlags) -> Alpm {
alpm_handle(inshandle.vars(), &*DEFAULT_ALPM_CONF, transflags, format!("{}/var/lib/pacman/", inshandle.vars().root()))
}
fn alpm_handle(insvars: &ContainerVariables, db_path: String, remotes: &AlpmConfigData) -> Alpm {
fn alpm_handle(insvars: &ContainerVariables, remotes: &AlpmConfigData, transflags: &TransactionFlags, db_path: String) -> Alpm {
let mut handle = Alpm::new(insvars.root(), &db_path).unwrap();
let debug = transflags.intersects(TransactionFlags::DEBUG);
if debug {
handle.set_log_cb(*UNIX_TIMESTAMP as usize, alpm_log_callback);
}
handle.set_disable_sandbox(CONFIG.alpm().disable_sandbox());
handle.set_cachedirs(vec![format!("{}/pkg", *CACHE_DIR)].iter()).unwrap();
@ -289,15 +302,16 @@ fn register_remote(mut handle: Alpm, config: &AlpmConfigData) -> Alpm {
handle
}
fn synchronize_database(cache: &ContainerCache, force: bool, lock: &Lock) -> Result<()> {
let handle = match cache.obtain_base_handle() {
fn synchronize_database(ag: &mut TransactionAggregator, force: bool) -> Result<()> {
let handle = match ag.cache().obtain_base_handle() {
Some(handle) => handle,
None => err!(SyncError::NoCompatibleRemotes)?,
};
let flags = ag.flags();
let db_path = format!("{}/pacman/", *DATA_DIR);
let mut handle = alpm_handle(&handle.vars(), db_path, &*DEFAULT_ALPM_CONF);
let mut handle = alpm_handle(&handle.vars(), &*DEFAULT_ALPM_CONF, flags, db_path);
lock.assert()?;
ag.lock()?.assert()?;
println!("{} {}Synchronizing package databases...{}", *BAR_GREEN, *BOLD, *RESET);
handle.set_dl_cb(DownloadEvent::new().style(&ProgressKind::Verbose), download::event);
@ -306,9 +320,9 @@ fn synchronize_database(cache: &ContainerCache, force: bool, lock: &Lock) -> Res
}
Alpm::release(handle).expect("Release Alpm handle");
lock.assert()?;
ag.lock()?.assert()?;
for handle in cache.filter_handle(vec![Base, Slice, Aggregate]).iter() {
for handle in ag.cache().filter_handle(vec![Base, Slice, Aggregate]).iter() {
for repo in PACMAN_CONF.repos.iter() {
let src = &format!("{}/pacman/sync/{}.db", *DATA_DIR, repo.name);
let dest = &format!("{}/var/lib/pacman/sync/{}.db", handle.vars().root(), repo.name);

View file

@ -97,16 +97,17 @@ pub trait Transaction {
}
bitflags! {
pub struct TransactionFlags: u8 {
pub struct TransactionFlags: u16 {
const NONE = 0;
const TARGET_ONLY = 0b00000001;
const PREVIEW = 0b00000010;
const NO_CONFIRM = 0b00000100;
const FORCE_DATABASE = 0b00001000;
const DATABASE_ONLY = 0b00010000;
const CREATE = 0b00100000;
const FILESYSTEM_SYNC = 0b01000000;
const LAZY_LOAD_DB = 0b10000000;
const TARGET_ONLY = 0b000000001;
const PREVIEW = 0b000000010;
const NO_CONFIRM = 0b000000100;
const FORCE_DATABASE = 0b000001000;
const DATABASE_ONLY = 0b000010000;
const CREATE = 0b000100000;
const FILESYSTEM_SYNC = 0b001000000;
const LAZY_LOAD_DB = 0b010000000;
const DEBUG = 0b100000000;
}
}
@ -127,7 +128,7 @@ pub struct TransactionMetadata<'a> {
held_pkgs: HashSet<String>,
queue: Vec<Cow<'a, str>>,
mode: TransactionMode,
flags: (u8, u32),
flags: (u16, u32),
}
#[derive(Serialize, Deserialize)]

View file

@ -19,7 +19,6 @@
use std::{
collections::{HashMap, HashSet},
env,
process::exit,
};
@ -30,7 +29,7 @@ use signal_hook::iterator::Signals;
use crate::{
config::{cache::ContainerCache, ContainerHandle, ContainerType::*},
constants::{ARROW_GREEN, IS_COLOR_TERMINAL, SIGNAL_LIST, UNIX_TIMESTAMP},
constants::{ARROW_GREEN, IS_COLOR_TERMINAL, SIGNAL_LIST, UNIX_TIMESTAMP, VERBOSE},
err,
error,
exec::{fakeroot_container, ExecutionType::NonInteractive},
@ -100,9 +99,7 @@ impl<'a> TransactionAggregator<'a> {
}
pub fn progress(mut self) -> Self {
if let (.., Remove(..)) | (.., Upgrade(false, true, ..)) | (false, ..) =
(*IS_COLOR_TERMINAL && !env::var("PACWRAP_VERBOSE").is_ok_and(|v| v == "1"), self.action)
{
if let (.., Remove(..)) | (.., Upgrade(false, true, ..)) | (false, ..) = (*IS_COLOR_TERMINAL && !*VERBOSE, self.action) {
return self;
}
@ -148,7 +145,7 @@ impl<'a> TransactionAggregator<'a> {
}
if refresh {
sync::synchronize_database(self.cache, force, self.lock()?)?;
sync::synchronize_database(&mut self, force)?;
}
upgrade | self.targets.is_some()
@ -243,7 +240,8 @@ impl<'a> TransactionAggregator<'a> {
Some(some) => some.clone(),
None => Vec::new(),
};
let alpm = sync::instantiate_alpm(&inshandle);
let alpm = sync::instantiate_alpm(&inshandle, &self.flags());
let mut meta = TransactionMetadata::new(queue);
let mut handle = TransactionHandle::new(&mut meta).alpm_handle(alpm);
let mut act: Box<dyn Transaction> = Prepare.from(self);

View file

@ -101,7 +101,7 @@ impl Transaction for Commit {
ag.keyring_update(inshandle)?;
}
handle.set_alpm(Some(sync::instantiate_alpm(inshandle)));
handle.set_alpm(Some(sync::instantiate_alpm(inshandle, &ag.flags())));
handle.apply_configuration(inshandle, ag.flags().intersects(TransactionFlags::CREATE))?;
ag.logger().log(Info, &format!("container {instance}'s {state} transaction complete"))?;
next_state(handle, ag.action(), &self.state, true)

View file

@ -69,7 +69,7 @@ impl Transaction for Prepare {
if deps.len() > 0 {
for dep in deps.iter().rev() {
match ag.cache().get_instance_option(dep) {
Some(dep_handle) => handle.enumerate_package_lists(&sync::instantiate_alpm(dep_handle)),
Some(dep_handle) => handle.enumerate_package_lists(&sync::instantiate_alpm(dep_handle, ag.flags())),
None => err!(SyncError::DependentContainerMissing(dep.to_string()))?,
}
}

View file

@ -182,6 +182,7 @@ fn engage_aggregator<'a>(args: &mut Arguments, lock: &'a Lock) -> Result<()> {
while let Some(arg) = args.next() {
match arg {
Op::Long("from-config") => continue,
Op::Long("debug") => flags = flags | TransactionFlags::DEBUG,
Op::Long("noconfirm") => flags = flags | TransactionFlags::NO_CONFIRM,
Op::Long("reinitialize-all") =>
for instance in cache.registered() {

View file

@ -24,7 +24,7 @@ use pacwrap_core::{
constants::{BOLD_GREEN, RESET},
err,
error::*,
sync::instantiate_alpm,
sync::{instantiate_alpm, transaction::TransactionFlags},
utils::{
arguments::{Arguments, InvalidArgument, Operand},
check_root,
@ -32,6 +32,7 @@ use pacwrap_core::{
};
pub fn query(arguments: &mut Arguments) -> Result<()> {
let mut flags: TransactionFlags = TransactionFlags::NONE;
let mut target = "";
let mut explicit = false;
let mut quiet = false;
@ -40,6 +41,7 @@ pub fn query(arguments: &mut Arguments) -> Result<()> {
while let Some(arg) = arguments.next() {
match arg {
Operand::Long("debug") => flags = flags | TransactionFlags::DEBUG,
Operand::Long("target") | Operand::Short('t') => continue,
Operand::Short('e') | Operand::Long("explicit") => explicit = true,
Operand::Short('q') | Operand::Long("quiet") => quiet = true,
@ -53,7 +55,7 @@ pub fn query(arguments: &mut Arguments) -> Result<()> {
}
let handle = config::provide_handle(target)?;
let handle = instantiate_alpm(&handle);
let handle = instantiate_alpm(&handle, &flags);
for pkg in handle.localdb().pkgs() {
if explicit && pkg.reason() != PackageReason::Explicit {

View file

@ -94,6 +94,7 @@ fn engage_aggregator<'a>(
| Op::Short('R')
| Op::Short('c')
| Op::Short('s') => continue,
Op::Long("debug") => flags = flags | TransactionFlags::DEBUG,
Op::Long("dbonly") => flags = flags | TransactionFlags::DATABASE_ONLY,
Op::Long("noconfirm") => flags = flags | TransactionFlags::NO_CONFIRM,
Op::Long("force-foreign") => flags = flags | TransactionFlags::FORCE_DATABASE,

View file

@ -170,6 +170,7 @@ fn engage_aggregator<'a>(
Op::Long("dbonly") => flags = flags | TransactionFlags::DATABASE_ONLY,
Op::Long("force-foreign") => flags = flags | TransactionFlags::FORCE_DATABASE,
Op::Long("noconfirm") => flags = flags | TransactionFlags::NO_CONFIRM,
Op::Long("debug") => flags = flags | TransactionFlags::DEBUG,
Op::Short('l') | Op::Long("lazy-load") => flags = flags | TransactionFlags::LAZY_LOAD_DB,
Op::Short('o') | Op::Long("target-only") => flags = flags | TransactionFlags::TARGET_ONLY,
Op::Short('f') | Op::Long("filesystem") => flags = flags | TransactionFlags::FILESYSTEM_SYNC,