We should be able to ndelay() from any context, even from an
interrupt context! However, this is broken (not functionally,
but locking-wise) in time-travel because we'll get into the
time-travel code and enable interrupts to handle messages on
other time-travel aware subsystems (only virtio for now).
Luckily, I've already reworked the time-travel aware signal
(interrupt) delivery for suspend/resume to have a time travel
handler, which runs directly in the context of the signal and
not from the Linux interrupt.
In order to fix this time-travel issue then, we need to do a
few things:
1) rework the signal handling code to call time-travel handlers
(only) if interrupts are disabled but signals aren't blocked,
instead of marking it only pending there. This is needed to
not deadlock other communication.
2) rework time-travel to not enable interrupts while it's
waiting for a message;
3) rework time-travel to not (just) disable interrupts but
rather block signals at a lower level while it needs them
disabled for communicating with the controller.
Finally, since now we can actually spend even virtual time
in interrupts-disabled sections, the delay warning when we
deliver a time-travel delayed interrupt is no longer valid,
things can (and should) now get delayed.
Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Signed-off-by: Richard Weinberger <richard@nod.at>
27 lines
595 B
C
27 lines
595 B
C
/* SPDX-License-Identifier: GPL-2.0 */
|
|
/*
|
|
* Copyright (C) 2001 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com)
|
|
*/
|
|
|
|
#ifndef __IRQ_USER_H__
|
|
#define __IRQ_USER_H__
|
|
|
|
#include <sysdep/ptrace.h>
|
|
#include <stdbool.h>
|
|
|
|
enum um_irq_type {
|
|
IRQ_READ,
|
|
IRQ_WRITE,
|
|
NUM_IRQ_TYPES,
|
|
};
|
|
|
|
struct siginfo;
|
|
extern void sigio_handler(int sig, struct siginfo *unused_si, struct uml_pt_regs *regs);
|
|
void sigio_run_timetravel_handlers(void);
|
|
extern void free_irq_by_fd(int fd);
|
|
extern void deactivate_fd(int fd, int irqnum);
|
|
extern int deactivate_all_fds(void);
|
|
extern int activate_ipi(int fd, int pid);
|
|
|
|
#endif
|