Compare commits
No commits in common. "0ff365c7f043f4972a8952cf77172ab97d089ad9" and "70bbdbd8f5683708bde8563e6b6381093c68dc30" have entirely different histories.
0ff365c7f0
...
70bbdbd8f5
|
@ -34,6 +34,4 @@ signal_trampoline:
|
|||
addl $8, %esp
|
||||
popf
|
||||
|
||||
movl (%esp), %esp
|
||||
|
||||
ret
|
||||
|
|
|
@ -59,7 +59,5 @@ signal_trampoline:
|
|||
addq $16, %rsp
|
||||
popfq
|
||||
|
||||
movq (%rsp), %rsp
|
||||
|
||||
// return over red-zone
|
||||
ret $128
|
||||
|
|
|
@ -1,179 +0,0 @@
|
|||
#pragma once
|
||||
|
||||
#include <BAN/ByteSpan.h>
|
||||
#include <BAN/Debug.h>
|
||||
#include <BAN/Optional.h>
|
||||
|
||||
namespace Kernel::ACPI
|
||||
{
|
||||
|
||||
struct ResourceData
|
||||
{
|
||||
enum class Type
|
||||
{
|
||||
IRQ,
|
||||
DMA,
|
||||
IOPort,
|
||||
FixedIOPort,
|
||||
FixedDMA,
|
||||
|
||||
// TODO: large stuff the stuff :)
|
||||
};
|
||||
|
||||
union {
|
||||
struct {
|
||||
uint16_t irq_mask;
|
||||
union {
|
||||
struct {
|
||||
uint8_t edge_triggered : 1;
|
||||
uint8_t : 2;
|
||||
uint8_t active_low : 1;
|
||||
uint8_t shared : 1;
|
||||
uint8_t wake_capable : 1;
|
||||
uint8_t : 2;
|
||||
};
|
||||
uint8_t raw;
|
||||
};
|
||||
} irq;
|
||||
struct {
|
||||
uint8_t channel_mask;
|
||||
union {
|
||||
struct {
|
||||
uint8_t type : 2; // 0: 8 bit, 1: 8 and 16 bit, 2: 16 bit only
|
||||
uint8_t bus_master : 1;
|
||||
uint8_t : 2;
|
||||
uint8_t channel_speed : 2; // 0: compatibility, 1: type A, 2: type B, 3: type F
|
||||
uint8_t : 1;
|
||||
};
|
||||
uint8_t raw;
|
||||
};
|
||||
} dma;
|
||||
struct {
|
||||
uint16_t range_min_base;
|
||||
uint16_t range_max_base;
|
||||
uint8_t base_alignment;
|
||||
uint8_t range_length;
|
||||
} io_port;
|
||||
struct {
|
||||
uint16_t range_base;
|
||||
uint8_t range_length;
|
||||
} fixed_io_port;
|
||||
struct {
|
||||
uint16_t request_line;
|
||||
uint16_t channel;
|
||||
uint8_t transfer_width; // 0: 8 bit, 1: 16 bit, 2: 32 bit, 3: 64 bit, 4: 128 bit
|
||||
} fixed_dma;
|
||||
} as;
|
||||
Type type;
|
||||
};
|
||||
|
||||
class ResourceParser
|
||||
{
|
||||
public:
|
||||
ResourceParser(BAN::ConstByteSpan buffer)
|
||||
: m_buffer(buffer)
|
||||
{}
|
||||
|
||||
BAN::Optional<ResourceData> get_next()
|
||||
{
|
||||
for (;;)
|
||||
{
|
||||
if (m_buffer.empty())
|
||||
return {};
|
||||
|
||||
if (m_buffer[0] & 0x80)
|
||||
{
|
||||
dprintln("Skipping large resource 0x{2H}", m_buffer[0] & 0x7F);
|
||||
const uint16_t length = (m_buffer[2] << 8) | m_buffer[1];
|
||||
if (m_buffer.size() < static_cast<size_t>(3 + length))
|
||||
return {};
|
||||
m_buffer = m_buffer.slice(3 + length);
|
||||
continue;
|
||||
}
|
||||
|
||||
const uint8_t length = m_buffer[0] & 0x07;
|
||||
if (m_buffer.size() < static_cast<size_t>(1 + length))
|
||||
return {};
|
||||
|
||||
BAN::Optional<ResourceData> result;
|
||||
switch ((m_buffer[0] >> 3) & 0x0F)
|
||||
{
|
||||
case 0x04:
|
||||
if (length < 2)
|
||||
break;
|
||||
result = ResourceData {
|
||||
.as = { .irq = {
|
||||
.irq_mask = static_cast<uint16_t>((m_buffer[2] << 8) | m_buffer[1]),
|
||||
.raw = (length >= 3) ? m_buffer[3] : static_cast<uint8_t>(1),
|
||||
}},
|
||||
.type = ResourceData::Type::IRQ,
|
||||
};
|
||||
break;
|
||||
case 0x05:
|
||||
if (length < 2)
|
||||
break;
|
||||
result = ResourceData {
|
||||
.as = { .dma = {
|
||||
.channel_mask = m_buffer[1],
|
||||
.raw = m_buffer[2],
|
||||
}},
|
||||
.type = ResourceData::Type::DMA,
|
||||
};
|
||||
break;
|
||||
case 0x08:
|
||||
if (length < 7)
|
||||
break;
|
||||
result = ResourceData {
|
||||
.as = { .io_port = {
|
||||
.range_min_base = static_cast<uint16_t>(((m_buffer[3] << 8) | m_buffer[2]) & ((m_buffer[1] & 1) ? 0xFFFF : 0x03FF)),
|
||||
.range_max_base = static_cast<uint16_t>(((m_buffer[5] << 8) | m_buffer[4]) & ((m_buffer[1] & 1) ? 0xFFFF : 0x03FF)),
|
||||
.base_alignment = m_buffer[6],
|
||||
.range_length = m_buffer[7],
|
||||
}},
|
||||
.type = ResourceData::Type::IOPort,
|
||||
};
|
||||
break;
|
||||
case 0x09:
|
||||
if (length < 3)
|
||||
break;
|
||||
result = ResourceData {
|
||||
.as = { .fixed_io_port = {
|
||||
.range_base = static_cast<uint16_t>(((m_buffer[2] << 8) | m_buffer[1]) & 0x03FF),
|
||||
.range_length = m_buffer[3],
|
||||
}},
|
||||
.type = ResourceData::Type::FixedIOPort,
|
||||
};
|
||||
break;
|
||||
case 0x0A:
|
||||
if (length < 5)
|
||||
break;
|
||||
result = ResourceData {
|
||||
.as = { .fixed_dma = {
|
||||
.request_line = static_cast<uint16_t>((m_buffer[2] << 8) | m_buffer[1]),
|
||||
.channel = static_cast<uint16_t>((m_buffer[4] << 8) | m_buffer[3]),
|
||||
.transfer_width = m_buffer[5],
|
||||
}},
|
||||
.type = ResourceData::Type::FixedDMA,
|
||||
};
|
||||
break;
|
||||
case 0x0F:
|
||||
// End tag
|
||||
return {};
|
||||
case 0x06:
|
||||
case 0x07:
|
||||
case 0x0E:
|
||||
dprintln("Skipping short resource 0x{2H}", (m_buffer[0] >> 3) & 0x0F);
|
||||
break;
|
||||
}
|
||||
|
||||
m_buffer = m_buffer.slice(1 + length);
|
||||
if (result.has_value())
|
||||
return result.release_value();
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
BAN::ConstByteSpan m_buffer;
|
||||
};
|
||||
|
||||
}
|
|
@ -193,9 +193,6 @@ namespace Kernel
|
|||
BAN::ErrorOr<long> sys_sigaction(int signal, const struct sigaction* act, struct sigaction* oact);
|
||||
BAN::ErrorOr<long> sys_sigpending(sigset_t* set);
|
||||
BAN::ErrorOr<long> sys_sigprocmask(int how, const sigset_t* set, sigset_t* oset);
|
||||
BAN::ErrorOr<long> sys_sigsuspend(const sigset_t* set);
|
||||
BAN::ErrorOr<long> sys_sigwait(const sigset_t* set, int* sig);
|
||||
BAN::ErrorOr<long> sys_sigaltstack(const stack_t* ss, stack_t* oss);
|
||||
|
||||
BAN::ErrorOr<long> sys_futex(int op, const uint32_t* addr, uint32_t val, const timespec* abstime);
|
||||
BAN::ErrorOr<long> sys_yield();
|
||||
|
@ -350,6 +347,14 @@ namespace Kernel
|
|||
BAN::UniqPtr<PageTable> m_page_table;
|
||||
BAN::RefPtr<TTY> m_controlling_terminal;
|
||||
|
||||
struct futex_t
|
||||
{
|
||||
ThreadBlocker blocker;
|
||||
uint32_t waiters { 0 };
|
||||
uint32_t to_wakeup { 0 };
|
||||
};
|
||||
BAN::HashMap<paddr_t, BAN::UniqPtr<futex_t>> m_futexes;
|
||||
|
||||
friend class Thread;
|
||||
};
|
||||
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
#pragma once
|
||||
|
||||
#include <BAN/NoCopyMove.h>
|
||||
#include <BAN/Optional.h>
|
||||
#include <BAN/RefPtr.h>
|
||||
#include <BAN/UniqPtr.h>
|
||||
#include <kernel/InterruptStack.h>
|
||||
|
@ -60,10 +59,7 @@ namespace Kernel
|
|||
bool will_execute_signal() const;
|
||||
// Returns true if handled signal had SA_RESTART
|
||||
bool handle_signal(int signal = 0);
|
||||
void add_signal(int signal);
|
||||
void set_suspend_signal_mask(uint64_t sigmask);
|
||||
|
||||
BAN::ErrorOr<void> sigaltstack(const stack_t* ss, stack_t* oss);
|
||||
bool add_signal(int signal);
|
||||
|
||||
// blocks current thread and returns either on unblock, eintr, spuriously or after timeout
|
||||
// if mutex is not nullptr, it will be atomically freed before blocking and automatically locked on wake
|
||||
|
@ -142,8 +138,6 @@ namespace Kernel
|
|||
static void on_exit_trampoline(Thread*);
|
||||
void on_exit();
|
||||
|
||||
bool currently_on_alternate_stack() const;
|
||||
|
||||
private:
|
||||
// NOTE: this is the first member to force it being last destructed
|
||||
// {kernel,userspace}_stack has to be destroyed before page table
|
||||
|
@ -166,9 +160,7 @@ namespace Kernel
|
|||
|
||||
uint64_t m_signal_pending_mask { 0 };
|
||||
uint64_t m_signal_block_mask { 0 };
|
||||
BAN::Optional<uint64_t> m_signal_suspend_mask;
|
||||
SpinLock m_signal_lock;
|
||||
stack_t m_signal_alt_stack { nullptr, 0, SS_DISABLE };
|
||||
static_assert(_SIGMAX < 64);
|
||||
|
||||
mutable SpinLock m_cpu_time_lock;
|
||||
|
|
|
@ -438,7 +438,7 @@ namespace Kernel::ACPI::AML
|
|||
{
|
||||
dprintln_if(AML_DUMP_FUNCTION_CALLS, "find_named_object('{}', '{}')", scope, name_string);
|
||||
|
||||
if (force_absolute || name_string.base != 0 || name_string.parts.size() > 1)
|
||||
if (force_absolute || name_string.base != 0)
|
||||
{
|
||||
// Absolute path
|
||||
|
||||
|
@ -460,15 +460,23 @@ namespace Kernel::ACPI::AML
|
|||
// Relative path
|
||||
|
||||
Scope path_guess;
|
||||
TRY(path_guess.parts.reserve(scope.parts.size() + 1));
|
||||
const uint32_t name_seg = name_string.parts.front();
|
||||
|
||||
TRY(path_guess.parts.reserve(scope.parts.size() + name_string.parts.size()));
|
||||
for (const auto& part : scope.parts)
|
||||
TRY(path_guess.parts.push_back(part));
|
||||
TRY(path_guess.parts.push_back(name_seg));
|
||||
for (const auto& part : name_string.parts)
|
||||
TRY(path_guess.parts.push_back(part));
|
||||
|
||||
for (;;)
|
||||
auto it = m_named_objects.find(path_guess);
|
||||
if (it != m_named_objects.end()) {
|
||||
return FindResult {
|
||||
.path = BAN::move(path_guess),
|
||||
.node = it->value,
|
||||
};
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < scope.parts.size(); i++)
|
||||
{
|
||||
path_guess.parts.remove(scope.parts.size() - i - 1);
|
||||
auto it = m_named_objects.find(path_guess);
|
||||
if (it != m_named_objects.end()) {
|
||||
return FindResult {
|
||||
|
@ -476,17 +484,12 @@ namespace Kernel::ACPI::AML
|
|||
.node = it->value,
|
||||
};
|
||||
}
|
||||
|
||||
if (path_guess.parts.size() == 1) {
|
||||
return FindResult {
|
||||
.path = {},
|
||||
.node = nullptr,
|
||||
};
|
||||
}
|
||||
|
||||
path_guess.parts.pop_back();
|
||||
path_guess.parts.back() = name_seg;
|
||||
}
|
||||
|
||||
return FindResult {
|
||||
.path = {},
|
||||
.node = nullptr,
|
||||
};
|
||||
}
|
||||
|
||||
BAN::ErrorOr<Scope> Namespace::find_reference_scope(const Reference* reference)
|
||||
|
|
|
@ -30,19 +30,19 @@ namespace Kernel
|
|||
|
||||
timespec FATInode::atime() const
|
||||
{
|
||||
const time_t epoch = fat_date_to_epoch(m_entry.last_access_date, {});
|
||||
uint64_t epoch = fat_date_to_epoch(m_entry.last_access_date, {});
|
||||
return timespec { .tv_sec = epoch, .tv_nsec = 0 };
|
||||
}
|
||||
|
||||
timespec FATInode::mtime() const
|
||||
{
|
||||
const time_t epoch = fat_date_to_epoch(m_entry.write_date, m_entry.write_time);
|
||||
uint64_t epoch = fat_date_to_epoch(m_entry.write_date, m_entry.write_time);
|
||||
return timespec { .tv_sec = epoch, .tv_nsec = 0 };
|
||||
}
|
||||
|
||||
timespec FATInode::ctime() const
|
||||
{
|
||||
const time_t epoch = fat_date_to_epoch(m_entry.creation_date, m_entry.creation_time);
|
||||
uint64_t epoch = fat_date_to_epoch(m_entry.creation_date, m_entry.creation_time);
|
||||
return timespec { .tv_sec = epoch, .tv_nsec = 0 };
|
||||
}
|
||||
|
||||
|
|
|
@ -256,84 +256,84 @@ namespace Kernel::Input
|
|||
|
||||
void PS2Keymap::initialize_scancode_set3()
|
||||
{
|
||||
m_scancode_to_keycode_normal[0x0E] = keycode_normal(0, 0);
|
||||
m_scancode_to_keycode_normal[0x16] = keycode_normal(0, 1);
|
||||
m_scancode_to_keycode_normal[0x1E] = keycode_normal(0, 2);
|
||||
m_scancode_to_keycode_normal[0x26] = keycode_normal(0, 3);
|
||||
m_scancode_to_keycode_normal[0x25] = keycode_normal(0, 4);
|
||||
m_scancode_to_keycode_normal[0x2E] = keycode_normal(0, 5);
|
||||
m_scancode_to_keycode_normal[0x36] = keycode_normal(0, 6);
|
||||
m_scancode_to_keycode_normal[0x3D] = keycode_normal(0, 7);
|
||||
m_scancode_to_keycode_normal[0x3E] = keycode_normal(0, 8);
|
||||
m_scancode_to_keycode_normal[0x46] = keycode_normal(0, 9);
|
||||
m_scancode_to_keycode_normal[0x45] = keycode_normal(0, 10);
|
||||
m_scancode_to_keycode_normal[0x4E] = keycode_normal(0, 11);
|
||||
m_scancode_to_keycode_normal[0x55] = keycode_normal(0, 12);
|
||||
m_scancode_to_keycode_normal[0x66] = keycode_normal(0, 13);
|
||||
m_scancode_to_keycode_normal[0x0D] = keycode_normal(1, 0);
|
||||
m_scancode_to_keycode_normal[0x15] = keycode_normal(1, 1);
|
||||
m_scancode_to_keycode_normal[0x1D] = keycode_normal(1, 2);
|
||||
m_scancode_to_keycode_normal[0x24] = keycode_normal(1, 3);
|
||||
m_scancode_to_keycode_normal[0x2D] = keycode_normal(1, 4);
|
||||
m_scancode_to_keycode_normal[0x2C] = keycode_normal(1, 5);
|
||||
m_scancode_to_keycode_normal[0x35] = keycode_normal(1, 6);
|
||||
m_scancode_to_keycode_normal[0x3C] = keycode_normal(1, 7);
|
||||
m_scancode_to_keycode_normal[0x43] = keycode_normal(1, 8);
|
||||
m_scancode_to_keycode_normal[0x44] = keycode_normal(1, 9);
|
||||
m_scancode_to_keycode_normal[0x4D] = keycode_normal(1, 10);
|
||||
m_scancode_to_keycode_normal[0x54] = keycode_normal(1, 11);
|
||||
m_scancode_to_keycode_normal[0x5B] = keycode_normal(1, 12);
|
||||
m_scancode_to_keycode_normal[0x14] = keycode_normal(2, 0);
|
||||
m_scancode_to_keycode_normal[0x1C] = keycode_normal(2, 1);
|
||||
m_scancode_to_keycode_normal[0x1B] = keycode_normal(2, 2);
|
||||
m_scancode_to_keycode_normal[0x23] = keycode_normal(2, 3);
|
||||
m_scancode_to_keycode_normal[0x2B] = keycode_normal(2, 4);
|
||||
m_scancode_to_keycode_normal[0x34] = keycode_normal(2, 5);
|
||||
m_scancode_to_keycode_normal[0x33] = keycode_normal(2, 6);
|
||||
m_scancode_to_keycode_normal[0x3B] = keycode_normal(2, 7);
|
||||
m_scancode_to_keycode_normal[0x42] = keycode_normal(2, 8);
|
||||
m_scancode_to_keycode_normal[0x4B] = keycode_normal(2, 9);
|
||||
m_scancode_to_keycode_normal[0x4C] = keycode_normal(2, 10);
|
||||
m_scancode_to_keycode_normal[0x52] = keycode_normal(2, 11);
|
||||
m_scancode_to_keycode_normal[0x5C] = keycode_normal(2, 12);
|
||||
m_scancode_to_keycode_normal[0x5A] = keycode_normal(2, 13);
|
||||
m_scancode_to_keycode_normal[0x12] = keycode_normal(3, 0);
|
||||
m_scancode_to_keycode_normal[0x13] = keycode_normal(3, 1);
|
||||
m_scancode_to_keycode_normal[0x1A] = keycode_normal(3, 2);
|
||||
m_scancode_to_keycode_normal[0x22] = keycode_normal(3, 3);
|
||||
m_scancode_to_keycode_normal[0x21] = keycode_normal(3, 4);
|
||||
m_scancode_to_keycode_normal[0x2A] = keycode_normal(3, 5);
|
||||
m_scancode_to_keycode_normal[0x32] = keycode_normal(3, 6);
|
||||
m_scancode_to_keycode_normal[0x31] = keycode_normal(3, 7);
|
||||
m_scancode_to_keycode_normal[0x3A] = keycode_normal(3, 8);
|
||||
m_scancode_to_keycode_normal[0x41] = keycode_normal(3, 9);
|
||||
m_scancode_to_keycode_normal[0x49] = keycode_normal(3, 10);
|
||||
m_scancode_to_keycode_normal[0x4A] = keycode_normal(3, 11);
|
||||
m_scancode_to_keycode_normal[0x59] = keycode_normal(3, 12);
|
||||
m_scancode_to_keycode_normal[0x11] = keycode_normal(4, 0);
|
||||
m_scancode_to_keycode_normal[0x8B] = keycode_normal(4, 1);
|
||||
m_scancode_to_keycode_normal[0x19] = keycode_normal(4, 2);
|
||||
m_scancode_to_keycode_normal[0x29] = keycode_normal(4, 3);
|
||||
m_scancode_to_keycode_normal[0x39] = keycode_normal(4, 4);
|
||||
m_scancode_to_keycode_normal[0x58] = keycode_normal(4, 5);
|
||||
m_scancode_to_keycode_normal[0x0E] = keycode_normal(0, 0);
|
||||
m_scancode_to_keycode_normal[0x16] = keycode_normal(0, 1);
|
||||
m_scancode_to_keycode_normal[0x1E] = keycode_normal(0, 2);
|
||||
m_scancode_to_keycode_normal[0x26] = keycode_normal(0, 3);
|
||||
m_scancode_to_keycode_normal[0x25] = keycode_normal(0, 4);
|
||||
m_scancode_to_keycode_normal[0x2E] = keycode_normal(0, 5);
|
||||
m_scancode_to_keycode_normal[0x36] = keycode_normal(0, 6);
|
||||
m_scancode_to_keycode_normal[0x3D] = keycode_normal(0, 7);
|
||||
m_scancode_to_keycode_normal[0x3E] = keycode_normal(0, 8);
|
||||
m_scancode_to_keycode_normal[0x46] = keycode_normal(0, 9);
|
||||
m_scancode_to_keycode_normal[0x45] = keycode_normal(0, 10);
|
||||
m_scancode_to_keycode_normal[0x4E] = keycode_normal(0, 11);
|
||||
m_scancode_to_keycode_normal[0x55] = keycode_normal(0, 12);
|
||||
m_scancode_to_keycode_normal[0x66] = keycode_normal(0, 13);
|
||||
m_scancode_to_keycode_normal[0x0D] = keycode_normal(1, 0);
|
||||
m_scancode_to_keycode_normal[0x15] = keycode_normal(1, 1);
|
||||
m_scancode_to_keycode_normal[0x1D] = keycode_normal(1, 2);
|
||||
m_scancode_to_keycode_normal[0x24] = keycode_normal(1, 3);
|
||||
m_scancode_to_keycode_normal[0x2D] = keycode_normal(1, 4);
|
||||
m_scancode_to_keycode_normal[0x2C] = keycode_normal(1, 5);
|
||||
m_scancode_to_keycode_normal[0x35] = keycode_normal(1, 6);
|
||||
m_scancode_to_keycode_normal[0x3C] = keycode_normal(1, 7);
|
||||
m_scancode_to_keycode_normal[0x43] = keycode_normal(1, 8);
|
||||
m_scancode_to_keycode_normal[0x44] = keycode_normal(1, 9);
|
||||
m_scancode_to_keycode_normal[0x4D] = keycode_normal(1, 10);
|
||||
m_scancode_to_keycode_normal[0x54] = keycode_normal(1, 11);
|
||||
m_scancode_to_keycode_normal[0x5B] = keycode_normal(1, 12);
|
||||
m_scancode_to_keycode_normal[0x14] = keycode_normal(2, 0);
|
||||
m_scancode_to_keycode_normal[0x1C] = keycode_normal(2, 1);
|
||||
m_scancode_to_keycode_normal[0x1B] = keycode_normal(2, 2);
|
||||
m_scancode_to_keycode_normal[0x23] = keycode_normal(2, 3);
|
||||
m_scancode_to_keycode_normal[0x2B] = keycode_normal(2, 4);
|
||||
m_scancode_to_keycode_normal[0x34] = keycode_normal(2, 5);
|
||||
m_scancode_to_keycode_normal[0x33] = keycode_normal(2, 6);
|
||||
m_scancode_to_keycode_normal[0x3B] = keycode_normal(2, 7);
|
||||
m_scancode_to_keycode_normal[0x42] = keycode_normal(2, 8);
|
||||
m_scancode_to_keycode_normal[0x4B] = keycode_normal(2, 9);
|
||||
m_scancode_to_keycode_normal[0x4C] = keycode_normal(2, 10);
|
||||
m_scancode_to_keycode_normal[0x52] = keycode_normal(2, 11);
|
||||
m_scancode_to_keycode_normal[0x5C] = keycode_normal(2, 12);
|
||||
m_scancode_to_keycode_normal[0x5A] = keycode_normal(2, 13);
|
||||
m_scancode_to_keycode_normal[0x12] = keycode_normal(3, 0);
|
||||
m_scancode_to_keycode_normal[0x13] = keycode_normal(3, 1);
|
||||
m_scancode_to_keycode_normal[0x1A] = keycode_normal(3, 2);
|
||||
m_scancode_to_keycode_normal[0x22] = keycode_normal(3, 3);
|
||||
m_scancode_to_keycode_normal[0x21] = keycode_normal(3, 4);
|
||||
m_scancode_to_keycode_normal[0x2A] = keycode_normal(3, 5);
|
||||
m_scancode_to_keycode_normal[0x32] = keycode_normal(3, 6);
|
||||
m_scancode_to_keycode_normal[0x31] = keycode_normal(3, 7);
|
||||
m_scancode_to_keycode_normal[0x3A] = keycode_normal(3, 8);
|
||||
m_scancode_to_keycode_normal[0x41] = keycode_normal(3, 9);
|
||||
m_scancode_to_keycode_normal[0x49] = keycode_normal(3, 10);
|
||||
m_scancode_to_keycode_normal[0x4A] = keycode_normal(3, 11);
|
||||
m_scancode_to_keycode_normal[0x59] = keycode_normal(3, 12);
|
||||
m_scancode_to_keycode_normal[0x11] = keycode_normal(4, 0);
|
||||
m_scancode_to_keycode_normal[0x8B] = keycode_normal(4, 1);
|
||||
m_scancode_to_keycode_normal[0x19] = keycode_normal(4, 2);
|
||||
m_scancode_to_keycode_normal[0x29] = keycode_normal(4, 3);
|
||||
m_scancode_to_keycode_normal[0x39] = keycode_normal(4, 4);
|
||||
m_scancode_to_keycode_normal[0x58] = keycode_normal(4, 5);
|
||||
|
||||
m_scancode_to_keycode_normal[0x76] = keycode_numpad(0, 0);
|
||||
m_scancode_to_keycode_normal[0x4A] = keycode_numpad(0, 1);
|
||||
//m_scancode_to_keycode_normal[0x] = keycode_numpad(0, 1);
|
||||
m_scancode_to_keycode_normal[0x7E] = keycode_numpad(0, 2);
|
||||
m_scancode_to_keycode_normal[0x4E] = keycode_numpad(0, 3);
|
||||
m_scancode_to_keycode_normal[0x6C] = keycode_numpad(1, 0);
|
||||
m_scancode_to_keycode_normal[0x75] = keycode_numpad(1, 1);
|
||||
m_scancode_to_keycode_normal[0x7D] = keycode_numpad(1, 2);
|
||||
m_scancode_to_keycode_normal[0x7C] = keycode_numpad(1, 3);
|
||||
m_scancode_to_keycode_normal[0x6B] = keycode_numpad(2, 0);
|
||||
m_scancode_to_keycode_normal[0x73] = keycode_numpad(2, 1);
|
||||
m_scancode_to_keycode_normal[0x74] = keycode_numpad(2, 2);
|
||||
m_scancode_to_keycode_normal[0x69] = keycode_numpad(3, 0);
|
||||
m_scancode_to_keycode_normal[0x72] = keycode_numpad(3, 1);
|
||||
m_scancode_to_keycode_normal[0x7A] = keycode_numpad(3, 2);
|
||||
m_scancode_to_keycode_normal[0x79] = keycode_numpad(3, 3);
|
||||
m_scancode_to_keycode_normal[0x70] = keycode_numpad(4, 0);
|
||||
m_scancode_to_keycode_normal[0x71] = keycode_numpad(4, 1);
|
||||
//m_scancode_to_keycode_normal[0x] = keycode_numpad(0, 3);
|
||||
m_scancode_to_keycode_normal[0x6C] = keycode_numpad(1, 1);
|
||||
m_scancode_to_keycode_normal[0x75] = keycode_numpad(1, 2);
|
||||
m_scancode_to_keycode_normal[0x7D] = keycode_numpad(1, 3);
|
||||
m_scancode_to_keycode_normal[0x7C] = keycode_numpad(1, 4);
|
||||
m_scancode_to_keycode_normal[0x6B] = keycode_numpad(2, 1);
|
||||
m_scancode_to_keycode_normal[0x73] = keycode_numpad(2, 2);
|
||||
m_scancode_to_keycode_normal[0x74] = keycode_numpad(2, 3);
|
||||
m_scancode_to_keycode_normal[0x69] = keycode_numpad(3, 1);
|
||||
m_scancode_to_keycode_normal[0x72] = keycode_numpad(3, 2);
|
||||
m_scancode_to_keycode_normal[0x7A] = keycode_numpad(3, 3);
|
||||
m_scancode_to_keycode_normal[0x79] = keycode_numpad(3, 4);
|
||||
m_scancode_to_keycode_normal[0x70] = keycode_numpad(4, 1);
|
||||
m_scancode_to_keycode_normal[0x71] = keycode_numpad(4, 2);
|
||||
|
||||
m_scancode_to_keycode_normal[0x08] = keycode_function(0);
|
||||
m_scancode_to_keycode_normal[0x07] = keycode_function(1);
|
||||
|
|
|
@ -289,10 +289,10 @@ namespace Kernel
|
|||
|
||||
BAN::ErrorOr<void> UnixDomainSocket::add_packet(BAN::ConstByteSpan packet)
|
||||
{
|
||||
SpinLockGuard guard(m_packet_lock);
|
||||
auto state = m_packet_lock.lock();
|
||||
while (m_packet_sizes.full() || m_packet_size_total + packet.size() > s_packet_buffer_size)
|
||||
{
|
||||
SpinLockGuardAsMutex smutex(guard);
|
||||
SpinLockAsMutex smutex(m_packet_lock, state);
|
||||
TRY(Thread::current().block_or_eintr_indefinite(m_packet_thread_blocker, &smutex));
|
||||
}
|
||||
|
||||
|
@ -304,6 +304,7 @@ namespace Kernel
|
|||
m_packet_sizes.push(packet.size());
|
||||
|
||||
m_packet_thread_blocker.unblock();
|
||||
m_packet_lock.unlock(state);
|
||||
|
||||
epoll_notify(EPOLLIN);
|
||||
|
||||
|
@ -413,7 +414,7 @@ namespace Kernel
|
|||
|
||||
BAN::ErrorOr<size_t> UnixDomainSocket::recvfrom_impl(BAN::ByteSpan buffer, sockaddr*, socklen_t*)
|
||||
{
|
||||
SpinLockGuard guard(m_packet_lock);
|
||||
auto state = m_packet_lock.lock();
|
||||
while (m_packet_size_total == 0)
|
||||
{
|
||||
if (m_info.has<ConnectionInfo>())
|
||||
|
@ -421,12 +422,18 @@ namespace Kernel
|
|||
auto& connection_info = m_info.get<ConnectionInfo>();
|
||||
bool expected = true;
|
||||
if (connection_info.target_closed.compare_exchange(expected, false))
|
||||
{
|
||||
m_packet_lock.unlock(state);
|
||||
return 0;
|
||||
}
|
||||
if (!connection_info.connection)
|
||||
{
|
||||
m_packet_lock.unlock(state);
|
||||
return BAN::Error::from_errno(ENOTCONN);
|
||||
}
|
||||
}
|
||||
|
||||
SpinLockGuardAsMutex smutex(guard);
|
||||
SpinLockAsMutex smutex(m_packet_lock, state);
|
||||
TRY(Thread::current().block_or_eintr_indefinite(m_packet_thread_blocker, &smutex));
|
||||
}
|
||||
|
||||
|
@ -446,6 +453,7 @@ namespace Kernel
|
|||
m_packet_size_total -= nread;
|
||||
|
||||
m_packet_thread_blocker.unblock();
|
||||
m_packet_lock.unlock(state);
|
||||
|
||||
epoll_notify(EPOLLOUT);
|
||||
|
||||
|
|
|
@ -37,15 +37,6 @@ namespace Kernel
|
|||
static BAN::Vector<Process*> s_processes;
|
||||
static RecursiveSpinLock s_process_lock;
|
||||
|
||||
struct futex_t
|
||||
{
|
||||
ThreadBlocker blocker;
|
||||
uint32_t waiters { 0 };
|
||||
uint32_t to_wakeup { 0 };
|
||||
};
|
||||
static BAN::HashMap<paddr_t, BAN::UniqPtr<futex_t>> s_futexes;
|
||||
static Mutex s_futex_lock;
|
||||
|
||||
static void for_each_process(const BAN::Function<BAN::Iteration(Process&)>& callback)
|
||||
{
|
||||
SpinLockGuard _(s_process_lock);
|
||||
|
@ -318,7 +309,7 @@ namespace Kernel
|
|||
LockGuard _(m_process_lock);
|
||||
for (auto* thread : m_threads)
|
||||
if (thread != &Thread::current())
|
||||
thread->add_signal(SIGKILL);
|
||||
ASSERT(thread->add_signal(SIGKILL));
|
||||
}
|
||||
|
||||
while (m_threads.size() > 1)
|
||||
|
@ -1167,10 +1158,8 @@ namespace Kernel
|
|||
BAN::ErrorOr<long> Process::sys_hardlinkat(int fd1, const char* path1, int fd2, const char* path2, int flag)
|
||||
{
|
||||
LockGuard _(m_process_lock);
|
||||
if (path1 != nullptr)
|
||||
TRY(validate_string_access(path1));
|
||||
if (path2 != nullptr)
|
||||
TRY(validate_string_access(path2));
|
||||
TRY(validate_string_access(path1));
|
||||
TRY(validate_string_access(path2));
|
||||
|
||||
auto inode = TRY(find_file(fd1, path1, flag)).inode;
|
||||
if (inode->mode().ifdir())
|
||||
|
@ -1191,8 +1180,7 @@ namespace Kernel
|
|||
return BAN::Error::from_errno(EINVAL);
|
||||
|
||||
LockGuard _(m_process_lock);
|
||||
if (path != nullptr)
|
||||
TRY(validate_string_access(path));
|
||||
TRY(validate_string_access(path));
|
||||
|
||||
auto [parent, file_name] = TRY(find_parent_file(fd, path, O_WRONLY));
|
||||
|
||||
|
@ -1207,8 +1195,7 @@ namespace Kernel
|
|||
BAN::ErrorOr<long> Process::sys_readlinkat(int fd, const char* path, char* buffer, size_t bufsize)
|
||||
{
|
||||
LockGuard _(m_process_lock);
|
||||
if (path != nullptr)
|
||||
TRY(validate_string_access(path));
|
||||
TRY(validate_string_access(path));
|
||||
TRY(validate_pointer_access(buffer, bufsize, true));
|
||||
|
||||
auto inode = TRY(find_file(fd, path, O_NOFOLLOW | O_RDONLY)).inode;
|
||||
|
@ -1275,8 +1262,7 @@ namespace Kernel
|
|||
flag = O_NOFOLLOW;
|
||||
|
||||
LockGuard _(m_process_lock);
|
||||
if (path != nullptr)
|
||||
TRY(validate_string_access(path));
|
||||
TRY(validate_string_access(path));
|
||||
|
||||
auto inode = TRY(find_file(fd, path, flag)).inode;
|
||||
|
||||
|
@ -1299,8 +1285,7 @@ namespace Kernel
|
|||
flag = O_NOFOLLOW;
|
||||
|
||||
LockGuard _(m_process_lock);
|
||||
if (path != nullptr)
|
||||
TRY(validate_string_access(path));
|
||||
TRY(validate_string_access(path));
|
||||
|
||||
auto inode = TRY(find_file(fd, path, flag)).inode;
|
||||
|
||||
|
@ -1986,8 +1971,6 @@ namespace Kernel
|
|||
flag = O_NOFOLLOW;
|
||||
|
||||
LockGuard _(m_process_lock);
|
||||
if (path != nullptr)
|
||||
TRY(validate_string_access(path));
|
||||
TRY(validate_pointer_access(buf, sizeof(struct stat), true));
|
||||
|
||||
auto inode = TRY(find_file(fd, path, flag)).inode;
|
||||
|
@ -2011,8 +1994,6 @@ namespace Kernel
|
|||
BAN::ErrorOr<long> Process::sys_fstatvfsat(int fd, const char* path, struct statvfs* buf)
|
||||
{
|
||||
LockGuard _(m_process_lock);
|
||||
if (path != nullptr)
|
||||
TRY(validate_string_access(path));
|
||||
TRY(validate_pointer_access(buf, sizeof(struct statvfs), true));
|
||||
|
||||
auto inode = TRY(find_file(fd, path, 0)).inode;
|
||||
|
@ -2177,17 +2158,6 @@ namespace Kernel
|
|||
vaddr_t base_addr = reinterpret_cast<vaddr_t>(args.addr);
|
||||
address_range.start = BAN::Math::div_round_up<vaddr_t>(base_addr, PAGE_SIZE) * PAGE_SIZE;
|
||||
address_range.end = BAN::Math::div_round_up<vaddr_t>(base_addr + args.len, PAGE_SIZE) * PAGE_SIZE;
|
||||
|
||||
for (size_t i = 0; i < m_mapped_regions.size(); i++)
|
||||
{
|
||||
if (!m_mapped_regions[i]->overlaps(base_addr, args.len))
|
||||
continue;
|
||||
if (!m_mapped_regions[i]->contains_fully(base_addr, args.len))
|
||||
derrorln("VERY BROKEN MAP_FIXED UNMAP");
|
||||
m_mapped_regions[i]->wait_not_pinned();
|
||||
m_mapped_regions.remove(i--);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (args.flags & MAP_ANONYMOUS)
|
||||
|
@ -2671,81 +2641,23 @@ namespace Kernel
|
|||
return 0;
|
||||
}
|
||||
|
||||
BAN::ErrorOr<long> Process::sys_sigsuspend(const sigset_t* set)
|
||||
{
|
||||
LockGuard _(m_process_lock);
|
||||
TRY(validate_pointer_access(set, sizeof(sigset_t), false));
|
||||
|
||||
auto& thread = Thread::current();
|
||||
thread.set_suspend_signal_mask(*set & ~(SIGKILL | SIGSTOP));
|
||||
|
||||
while (!thread.is_interrupted_by_signal())
|
||||
Processor::scheduler().block_current_thread(nullptr, -1, &m_process_lock);
|
||||
|
||||
return BAN::Error::from_errno(EINTR);
|
||||
}
|
||||
|
||||
BAN::ErrorOr<long> Process::sys_sigwait(const sigset_t* set, int* sig)
|
||||
{
|
||||
LockGuard _(m_process_lock);
|
||||
|
||||
auto& thread = Thread::current();
|
||||
for (;;)
|
||||
{
|
||||
TRY(validate_pointer_access(set, sizeof(sigset_t), false));
|
||||
TRY(validate_pointer_access(sig, sizeof(int), true));
|
||||
|
||||
{
|
||||
SpinLockGuard _1(thread.m_signal_lock);
|
||||
SpinLockGuard _2(m_signal_lock);
|
||||
|
||||
const uint64_t pending = thread.m_signal_pending_mask | this->m_signal_pending_mask;
|
||||
if (const auto wait_mask = pending & *set)
|
||||
{
|
||||
for (size_t i = _SIGMIN; i <= _SIGMAX; i++)
|
||||
{
|
||||
const auto mask = 1ull << i;
|
||||
if (!(wait_mask & mask))
|
||||
continue;
|
||||
thread.m_signal_pending_mask &= ~mask;
|
||||
this->m_signal_pending_mask &= ~mask;
|
||||
*sig = i;
|
||||
return 0;
|
||||
}
|
||||
|
||||
ASSERT_NOT_REACHED();
|
||||
}
|
||||
}
|
||||
|
||||
Processor::scheduler().block_current_thread(nullptr, -1, &m_process_lock);
|
||||
}
|
||||
}
|
||||
|
||||
BAN::ErrorOr<long> Process::sys_sigaltstack(const stack_t* ss, stack_t* oss)
|
||||
{
|
||||
LockGuard _(m_process_lock);
|
||||
if (ss != nullptr)
|
||||
TRY(validate_pointer_access(ss, sizeof(stack_t), false));
|
||||
if (oss != nullptr)
|
||||
TRY(validate_pointer_access(oss, sizeof(stack_t), true));
|
||||
|
||||
TRY(Thread::current().sigaltstack(ss, oss));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
BAN::ErrorOr<long> Process::sys_futex(int op, const uint32_t* addr, uint32_t val, const timespec* abstime)
|
||||
{
|
||||
const vaddr_t vaddr = reinterpret_cast<vaddr_t>(addr);
|
||||
if (vaddr % 4)
|
||||
return BAN::Error::from_errno(EINVAL);
|
||||
|
||||
const bool is_private = (op & FUTEX_PRIVATE);
|
||||
const bool is_realtime = (op & FUTEX_REALTIME);
|
||||
op &= ~(FUTEX_PRIVATE | FUTEX_REALTIME);
|
||||
|
||||
// TODO: possibly optimize private futexes?
|
||||
if (!is_private)
|
||||
{
|
||||
dwarnln("TODO: shared futex");
|
||||
return BAN::Error::from_errno(ENOTSUP);
|
||||
}
|
||||
|
||||
LockGuard _(s_futex_lock);
|
||||
LockGuard _(m_process_lock);
|
||||
|
||||
auto* buffer_region = TRY(validate_and_pin_pointer_access(addr, sizeof(uint32_t), false));
|
||||
BAN::ScopeGuard pin_guard([&] { if (buffer_region) buffer_region->unpin(); });
|
||||
|
@ -2776,20 +2688,20 @@ namespace Kernel
|
|||
return SystemTimer::get().ns_since_boot() + (abs_ns - real_ns);
|
||||
}());
|
||||
|
||||
auto it = s_futexes.find(paddr);
|
||||
if (it == s_futexes.end())
|
||||
it = TRY(s_futexes.emplace(paddr, TRY(BAN::UniqPtr<futex_t>::create())));
|
||||
auto it = m_futexes.find(paddr);
|
||||
if (it == m_futexes.end())
|
||||
it = TRY(m_futexes.emplace(paddr, TRY(BAN::UniqPtr<futex_t>::create())));
|
||||
futex_t* const futex = it->value.ptr();
|
||||
|
||||
futex->waiters++;
|
||||
BAN::ScopeGuard _([futex, paddr] {
|
||||
BAN::ScopeGuard _([futex, paddr, this] {
|
||||
if (--futex->waiters == 0)
|
||||
s_futexes.remove(paddr);
|
||||
m_futexes.remove(paddr);
|
||||
});
|
||||
|
||||
for (;;)
|
||||
{
|
||||
TRY(Thread::current().block_or_eintr_or_waketime_ns(futex->blocker, wake_time_ns, true, &s_futex_lock));
|
||||
TRY(Thread::current().block_or_eintr_or_waketime_ns(futex->blocker, wake_time_ns, true, &m_process_lock));
|
||||
if (BAN::atomic_load(*addr) == val || futex->to_wakeup == 0)
|
||||
continue;
|
||||
futex->to_wakeup--;
|
||||
|
@ -2798,8 +2710,8 @@ namespace Kernel
|
|||
}
|
||||
case FUTEX_WAKE:
|
||||
{
|
||||
auto it = s_futexes.find(paddr);
|
||||
if (it == s_futexes.end())
|
||||
auto it = m_futexes.find(paddr);
|
||||
if (it == m_futexes.end())
|
||||
return 0;
|
||||
futex_t* const futex = it->value.ptr();
|
||||
|
||||
|
@ -3299,10 +3211,8 @@ namespace Kernel
|
|||
BAN::ErrorOr<long> Process::sys_getgroups(gid_t groups[], size_t count)
|
||||
{
|
||||
LockGuard _(m_process_lock);
|
||||
const auto current = m_credentials.groups();
|
||||
if (count == 0)
|
||||
return current.size();
|
||||
TRY(validate_pointer_access(groups, count * sizeof(gid_t), true));
|
||||
auto current = m_credentials.groups();
|
||||
if (current.size() > count)
|
||||
return BAN::Error::from_errno(EINVAL);
|
||||
for (size_t i = 0; i < current.size(); i++)
|
||||
|
@ -3385,9 +3295,6 @@ unauthorized_access:
|
|||
{
|
||||
// TODO: This seems very slow as we loop over the range twice
|
||||
|
||||
if (size == 0)
|
||||
return {};
|
||||
|
||||
TRY(validate_pointer_access_check(ptr, size, needs_write));
|
||||
|
||||
const vaddr_t vaddr = reinterpret_cast<vaddr_t>(ptr);
|
||||
|
|
|
@ -92,14 +92,14 @@ namespace Kernel
|
|||
if (ret.is_error() && ret.error().is_kernel_error())
|
||||
Kernel::panic("Kernel error while returning to userspace {}", ret.error());
|
||||
|
||||
Processor::set_interrupt_state(InterruptState::Disabled);
|
||||
|
||||
auto& current_thread = Thread::current();
|
||||
if (current_thread.can_add_signal_to_execute())
|
||||
if (current_thread.handle_signal())
|
||||
if (ret.is_error() && ret.error().get_error_code() == EINTR && is_restartable_syscall(syscall))
|
||||
ret = BAN::Error::from_errno(ERESTART);
|
||||
|
||||
Processor::set_interrupt_state(InterruptState::Disabled);
|
||||
|
||||
ASSERT(Kernel::Thread::current().state() == Kernel::Thread::State::Executing);
|
||||
|
||||
if (ret.is_error())
|
||||
|
|
|
@ -165,7 +165,7 @@ namespace Kernel
|
|||
|
||||
PseudoTerminalSlave::PseudoTerminalSlave(BAN::String&& name, uint32_t number, mode_t mode, uid_t uid, gid_t gid)
|
||||
: TTY({
|
||||
.c_iflag = ICRNL,
|
||||
.c_iflag = 0,
|
||||
.c_oflag = 0,
|
||||
.c_cflag = CS8,
|
||||
.c_lflag = ECHO | ECHOE | ECHOK | ICANON | ISIG,
|
||||
|
|
|
@ -243,14 +243,19 @@ namespace Kernel
|
|||
|
||||
LockGuard _(m_mutex);
|
||||
|
||||
if ((m_termios.c_iflag & ISTRIP))
|
||||
ch &= 0x7F;
|
||||
if ((m_termios.c_iflag & IGNCR) && ch == CR)
|
||||
return;
|
||||
if ((m_termios.c_iflag & ICRNL) && ch == CR)
|
||||
ch = NL;
|
||||
else if ((m_termios.c_iflag & INLCR) && ch == NL)
|
||||
ch = CR;
|
||||
if (m_termios.c_lflag & ICANON)
|
||||
{
|
||||
if ((m_termios.c_iflag & ISTRIP))
|
||||
ch &= 0x7F;
|
||||
if ((m_termios.c_iflag & IGNCR) && ch == CR)
|
||||
return;
|
||||
uint8_t conv = ch;
|
||||
if ((m_termios.c_iflag & ICRNL) && ch == CR)
|
||||
conv = NL;
|
||||
if ((m_termios.c_iflag & INLCR) && ch == NL)
|
||||
conv = CR;
|
||||
ch = conv;
|
||||
}
|
||||
|
||||
if (m_termios.c_lflag & ISIG)
|
||||
{
|
||||
|
@ -293,10 +298,11 @@ namespace Kernel
|
|||
should_flush = true;
|
||||
}
|
||||
|
||||
if (ch == NL || ch == CR || ch == m_termios.c_cc[VEOL])
|
||||
if (ch == NL || ch == m_termios.c_cc[VEOL])
|
||||
{
|
||||
should_flush = true;
|
||||
force_echo = !!(m_termios.c_lflag & ECHONL);
|
||||
ch = NL;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -37,7 +37,7 @@ namespace Kernel
|
|||
|
||||
VirtualTTY::VirtualTTY(BAN::RefPtr<TerminalDriver> driver)
|
||||
: TTY({
|
||||
.c_iflag = ICRNL,
|
||||
.c_iflag = 0,
|
||||
.c_oflag = 0,
|
||||
.c_cflag = CS8,
|
||||
.c_lflag = ECHO | ECHOE | ECHOK | ICANON | ISIG,
|
||||
|
|
|
@ -69,20 +69,6 @@ namespace Kernel
|
|||
s_default_sse_storage_initialized = true;
|
||||
}
|
||||
|
||||
static bool is_default_ignored_signal(int signal)
|
||||
{
|
||||
switch (signal)
|
||||
{
|
||||
case SIGCHLD:
|
||||
case SIGURG:
|
||||
case SIGWINCH:
|
||||
case SIGCANCEL:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
BAN::ErrorOr<Thread*> Thread::create_kernel(entry_t entry, void* data)
|
||||
{
|
||||
// Create the thread object
|
||||
|
@ -481,7 +467,7 @@ namespace Kernel
|
|||
}
|
||||
if (signal_handler == (vaddr_t)SIG_IGN)
|
||||
continue;
|
||||
if (signal_handler == (vaddr_t)SIG_DFL && is_default_ignored_signal(i))
|
||||
if (signal_handler == (vaddr_t)SIG_DFL && (i == SIGCHLD || i == SIGURG))
|
||||
continue;
|
||||
return true;
|
||||
}
|
||||
|
@ -507,7 +493,6 @@ namespace Kernel
|
|||
ASSERT(is_userspace());
|
||||
|
||||
auto state = m_signal_lock.lock();
|
||||
ASSERT(state == InterruptState::Disabled);
|
||||
|
||||
auto& interrupt_stack = *reinterpret_cast<InterruptStack*>(kernel_stack_top() - sizeof(InterruptStack));
|
||||
ASSERT(GDT::is_user_segment(interrupt_stack.cs));
|
||||
|
@ -531,7 +516,6 @@ namespace Kernel
|
|||
|
||||
vaddr_t signal_handler;
|
||||
bool has_sa_restart;
|
||||
vaddr_t signal_stack_top = 0;
|
||||
{
|
||||
SpinLockGuard _(m_process->m_signal_lock);
|
||||
|
||||
|
@ -544,23 +528,11 @@ namespace Kernel
|
|||
handler.sa_handler = SIG_DFL;
|
||||
|
||||
has_sa_restart = !!(handler.sa_flags & SA_RESTART);
|
||||
|
||||
const auto& alt_stack = m_signal_alt_stack;
|
||||
if (alt_stack.ss_flags != SS_DISABLE && (handler.sa_flags & SA_ONSTACK) && !currently_on_alternate_stack())
|
||||
signal_stack_top = reinterpret_cast<vaddr_t>(alt_stack.ss_sp) + alt_stack.ss_size;
|
||||
}
|
||||
|
||||
m_signal_pending_mask &= ~(1ull << signal);
|
||||
process().remove_pending_signal(signal);
|
||||
|
||||
if (m_signal_suspend_mask.has_value())
|
||||
{
|
||||
m_signal_block_mask = m_signal_suspend_mask.value();
|
||||
m_signal_suspend_mask.clear();
|
||||
}
|
||||
|
||||
m_signal_lock.unlock(state);
|
||||
|
||||
if (signal_handler == (vaddr_t)SIG_IGN)
|
||||
;
|
||||
else if (signal_handler != (vaddr_t)SIG_DFL)
|
||||
|
@ -569,32 +541,7 @@ namespace Kernel
|
|||
#if ARCH(x86_64)
|
||||
interrupt_stack.sp -= 128; // skip possible red-zone
|
||||
#endif
|
||||
|
||||
{
|
||||
// Make sure stack is allocated
|
||||
|
||||
const vaddr_t pages[3] {
|
||||
(interrupt_stack.sp - sizeof(uintptr_t)) & PAGE_ADDR_MASK,
|
||||
(signal_stack_top - 4 * sizeof(uintptr_t)) & PAGE_ADDR_MASK,
|
||||
(signal_stack_top - 1 * sizeof(uintptr_t)) & PAGE_ADDR_MASK,
|
||||
};
|
||||
|
||||
for (size_t i = 0; i < 3; i++)
|
||||
{
|
||||
if (m_process->page_table().get_page_flags(pages[i]) & PageTable::Flags::Present)
|
||||
continue;
|
||||
Processor::set_interrupt_state(InterruptState::Enabled);
|
||||
if (auto ret = m_process->allocate_page_for_demand_paging(pages[i], true, false); ret.is_error() || !ret.value())
|
||||
m_process->exit(128 + SIGSEGV, SIGSEGV);
|
||||
Processor::set_interrupt_state(InterruptState::Disabled);
|
||||
}
|
||||
}
|
||||
|
||||
write_to_stack(interrupt_stack.sp, interrupt_stack.ip);
|
||||
const vaddr_t old_stack = interrupt_stack.sp;
|
||||
if (signal_stack_top)
|
||||
interrupt_stack.sp = signal_stack_top;
|
||||
write_to_stack(interrupt_stack.sp, old_stack);
|
||||
write_to_stack(interrupt_stack.sp, interrupt_stack.flags);
|
||||
write_to_stack(interrupt_stack.sp, signal);
|
||||
write_to_stack(interrupt_stack.sp, signal_handler);
|
||||
|
@ -615,6 +562,7 @@ namespace Kernel
|
|||
case SIGTRAP:
|
||||
case SIGXCPU:
|
||||
case SIGXFSZ:
|
||||
m_signal_lock.unlock(state);
|
||||
process().exit(128 + signal, signal | 0x80);
|
||||
ASSERT_NOT_REACHED();
|
||||
|
||||
|
@ -630,11 +578,18 @@ namespace Kernel
|
|||
case SIGPOLL:
|
||||
case SIGPROF:
|
||||
case SIGVTALRM:
|
||||
m_signal_lock.unlock(state);
|
||||
process().exit(128 + signal, signal);
|
||||
ASSERT_NOT_REACHED();
|
||||
|
||||
// Ignore the signal
|
||||
case SIGCHLD:
|
||||
case SIGURG:
|
||||
case SIGWINCH:
|
||||
case SIGCANCEL:
|
||||
break;
|
||||
|
||||
// Stop the process:
|
||||
case SIGSTOP:
|
||||
case SIGTSTP:
|
||||
case SIGTTIN:
|
||||
case SIGTTOU:
|
||||
|
@ -643,18 +598,15 @@ namespace Kernel
|
|||
// Continue the process, if it is stopped; otherwise, ignore the signal.
|
||||
case SIGCONT:
|
||||
ASSERT_NOT_REACHED();
|
||||
|
||||
default:
|
||||
if (is_default_ignored_signal(signal))
|
||||
break;
|
||||
panic("Executing unhandled signal {}", signal);
|
||||
}
|
||||
}
|
||||
|
||||
m_signal_lock.unlock(state);
|
||||
|
||||
return has_sa_restart;
|
||||
}
|
||||
|
||||
void Thread::add_signal(int signal)
|
||||
bool Thread::add_signal(int signal)
|
||||
{
|
||||
SpinLockGuard _(m_signal_lock);
|
||||
if (m_process)
|
||||
|
@ -666,64 +618,19 @@ namespace Kernel
|
|||
signal_handler = (vaddr_t)m_process->m_signal_handlers[signal].sa_handler;
|
||||
}
|
||||
if (signal_handler == (vaddr_t)SIG_IGN)
|
||||
return;
|
||||
if (signal_handler == (vaddr_t)SIG_DFL && is_default_ignored_signal(signal))
|
||||
return;
|
||||
return false;
|
||||
if (signal_handler == (vaddr_t)SIG_DFL && (signal == SIGCHLD || signal == SIGURG))
|
||||
return false;
|
||||
}
|
||||
|
||||
const uint64_t mask = 1ull << signal;
|
||||
m_signal_pending_mask |= mask;
|
||||
|
||||
if (this != &Thread::current())
|
||||
Processor::scheduler().unblock_thread(this);
|
||||
}
|
||||
|
||||
void Thread::set_suspend_signal_mask(uint64_t sigmask)
|
||||
{
|
||||
SpinLockGuard _(m_signal_lock);
|
||||
ASSERT(!m_signal_suspend_mask.has_value());
|
||||
m_signal_suspend_mask = m_signal_block_mask;
|
||||
m_signal_block_mask = sigmask;
|
||||
}
|
||||
|
||||
bool Thread::currently_on_alternate_stack() const
|
||||
{
|
||||
ASSERT(m_signal_lock.current_processor_has_lock());
|
||||
|
||||
if (m_signal_alt_stack.ss_flags == SS_ONSTACK)
|
||||
return false;
|
||||
|
||||
const vaddr_t stack_bottom = reinterpret_cast<vaddr_t>(m_signal_alt_stack.ss_sp);
|
||||
const vaddr_t stack_top = stack_bottom + m_signal_alt_stack.ss_size;
|
||||
const vaddr_t sp = m_interrupt_stack.sp;
|
||||
return stack_bottom <= sp && sp <= stack_top;
|
||||
}
|
||||
|
||||
BAN::ErrorOr<void> Thread::sigaltstack(const stack_t* ss, stack_t* oss)
|
||||
{
|
||||
SpinLockGuard _(m_signal_lock);
|
||||
|
||||
const bool on_alt_stack = currently_on_alternate_stack();
|
||||
|
||||
if (oss)
|
||||
uint64_t mask = 1ull << signal;
|
||||
if (!(m_signal_block_mask & mask))
|
||||
{
|
||||
*oss = m_signal_alt_stack;
|
||||
if (on_alt_stack)
|
||||
oss->ss_flags = SS_ONSTACK;
|
||||
m_signal_pending_mask |= mask;
|
||||
if (this != &Thread::current())
|
||||
Processor::scheduler().unblock_thread(this);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ss)
|
||||
{
|
||||
if (on_alt_stack)
|
||||
return BAN::Error::from_errno(EPERM);
|
||||
if (ss->ss_flags && ss->ss_flags != SS_DISABLE)
|
||||
return BAN::Error::from_errno(EINVAL);
|
||||
if (ss->ss_size < MINSIGSTKSZ)
|
||||
return BAN::Error::from_errno(ENOMEM);
|
||||
m_signal_alt_stack = *ss;
|
||||
}
|
||||
|
||||
return {};
|
||||
return false;
|
||||
}
|
||||
|
||||
BAN::ErrorOr<void> Thread::sleep_or_eintr_ns(uint64_t ns)
|
||||
|
|
|
@ -299,7 +299,7 @@ namespace Kernel
|
|||
long ns_this_second = ticks_this_second * regs.counter_clk_period / FS_PER_NS;
|
||||
|
||||
return timespec {
|
||||
.tv_sec = static_cast<time_t>(seconds),
|
||||
.tv_sec = seconds,
|
||||
.tv_nsec = ns_this_second
|
||||
};
|
||||
}
|
||||
|
|
|
@ -487,8 +487,8 @@ diff -ruN SDL2-2.32.8/src/video/banan_os/SDL_banan_os_message_box.h SDL2-2.32.8-
|
|||
+/* vi: set ts=4 sw=4 expandtab: */
|
||||
diff -ruN SDL2-2.32.8/src/video/banan_os/SDL_banan_os_video.cpp SDL2-2.32.8-banan_os/src/video/banan_os/SDL_banan_os_video.cpp
|
||||
--- SDL2-2.32.8/src/video/banan_os/SDL_banan_os_video.cpp 1970-01-01 02:00:00.000000000 +0200
|
||||
+++ SDL2-2.32.8-banan_os/src/video/banan_os/SDL_banan_os_video.cpp 2025-08-21 02:32:59.649175565 +0300
|
||||
@@ -0,0 +1,724 @@
|
||||
+++ SDL2-2.32.8-banan_os/src/video/banan_os/SDL_banan_os_video.cpp 2025-08-06 02:01:21.086666679 +0300
|
||||
@@ -0,0 +1,718 @@
|
||||
+/*
|
||||
+ Simple DirectMedia Layer
|
||||
+ Copyright (C) 1997-2025 Sam Lantinga <slouken@libsdl.org>
|
||||
|
@ -894,12 +894,6 @@ diff -ruN SDL2-2.32.8/src/video/banan_os/SDL_banan_os_video.cpp SDL2-2.32.8-bana
|
|||
+ }
|
||||
+ );
|
||||
+
|
||||
+ ban_window->window->set_window_focus_event_callback(
|
||||
+ [window](LibGUI::EventPacket::WindowFocusEvent::event_t event) {
|
||||
+ SDL_SetKeyboardFocus(event.focused ? window : nullptr);
|
||||
+ }
|
||||
+ );
|
||||
+
|
||||
+ ban_window->window->set_close_window_event_callback(
|
||||
+ [window]() {
|
||||
+ SDL_SendWindowEvent(window, SDL_WINDOWEVENT_CLOSE, 0, 0);
|
||||
|
|
|
@ -3,16 +3,15 @@
|
|||
NAME='SDL2_mixer'
|
||||
VERSION='2.8.1'
|
||||
DOWNLOAD_URL="https://github.com/libsdl-org/SDL_mixer/releases/download/release-$VERSION/SDL2_mixer-$VERSION.tar.gz#cb760211b056bfe44f4a1e180cc7cb201137e4d1572f2002cc1be728efd22660"
|
||||
DEPENDENCIES=('SDL2' 'timidity')
|
||||
DEPENDENCIES=('SDL2')
|
||||
|
||||
configure() {
|
||||
$BANAN_CMAKE --fresh -S . -B build -G Ninja \
|
||||
--toolchain="$BANAN_TOOLCHAIN_DIR/Toolchain.txt" \
|
||||
-DCMAKE_INSTALL_PREFIX='/usr' \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DSDL2MIXER_DEPS_SHARED=OFF \
|
||||
-DSDL2MIXER_MIDI_FLUIDSYNTH=OFF \
|
||||
-DSDL2MIXER_WAVPACK=OFF \
|
||||
-DSDL2MIXER_MIDI=OFF \
|
||||
-DSDL2MIXER_OPUS=OFF \
|
||||
-DSDL2MIXER_MOD=OFF \
|
||||
|| exit 1
|
||||
|
|
|
@ -1,26 +0,0 @@
|
|||
#!/bin/bash ../install.sh
|
||||
|
||||
NAME='glib'
|
||||
VERSION='2.85.2'
|
||||
DOWNLOAD_URL="https://download.gnome.org/sources/glib/${VERSION%.*}/glib-$VERSION.tar.xz#833b97c0f0a1bfdba1d0fbfc36cd368b855c5afd9f02b8ffb24129114ad051b2"
|
||||
DEPENDENCIES=('pcre2' 'libffi' 'zlib' 'libiconv')
|
||||
CONFIGURE_OPTIONS=(
|
||||
'-Dprefix=/usr'
|
||||
'-Dxattr=false'
|
||||
)
|
||||
|
||||
configure() {
|
||||
meson setup \
|
||||
--reconfigure \
|
||||
--cross-file "$MESON_CROSS_FILE" \
|
||||
"${CONFIGURE_OPTIONS[@]}" \
|
||||
build || exit 1
|
||||
}
|
||||
|
||||
build() {
|
||||
meson compile -C build || exit 1
|
||||
}
|
||||
|
||||
install() {
|
||||
meson install --destdir="$BANAN_SYSROOT" -C build || exit 1
|
||||
}
|
|
@ -1,106 +0,0 @@
|
|||
diff -ruN glib-2.85.2/gio/gnetworking.h.in glib-2.85.2-banan_os/gio/gnetworking.h.in
|
||||
--- glib-2.85.2/gio/gnetworking.h.in 2025-07-21 20:47:53.000000000 +0300
|
||||
+++ glib-2.85.2-banan_os/gio/gnetworking.h.in 2025-08-19 18:21:06.038296386 +0300
|
||||
@@ -40,13 +40,17 @@
|
||||
#include <netdb.h>
|
||||
#include <netinet/in.h>
|
||||
#include <netinet/tcp.h>
|
||||
+#ifndef __banan_os__
|
||||
#include <resolv.h>
|
||||
+#endif
|
||||
#include <sys/socket.h>
|
||||
#include <sys/un.h>
|
||||
#include <net/if.h>
|
||||
|
||||
#include <arpa/inet.h>
|
||||
+#ifndef __banan_os__
|
||||
#include <arpa/nameser.h>
|
||||
+#endif
|
||||
@NAMESER_COMPAT_INCLUDE@
|
||||
|
||||
#ifndef __GI_SCANNER__
|
||||
diff -ruN glib-2.85.2/gio/gthreadedresolver.c glib-2.85.2-banan_os/gio/gthreadedresolver.c
|
||||
--- glib-2.85.2/gio/gthreadedresolver.c 2025-07-21 20:47:53.000000000 +0300
|
||||
+++ glib-2.85.2-banan_os/gio/gthreadedresolver.c 2025-08-19 18:21:06.052332130 +0300
|
||||
@@ -41,6 +41,10 @@
|
||||
#include "gsocketaddress.h"
|
||||
#include "gsrvtarget.h"
|
||||
|
||||
+#if defined __banan_os__
|
||||
+#include <endian.h>
|
||||
+#endif
|
||||
+
|
||||
#if HAVE_GETIFADDRS
|
||||
#include <ifaddrs.h>
|
||||
#endif
|
||||
@@ -692,7 +696,7 @@
|
||||
|
||||
#if defined(G_OS_UNIX)
|
||||
|
||||
-#if defined __BIONIC__ && !defined BIND_4_COMPAT
|
||||
+#if (defined __BIONIC__ && !defined BIND_4_COMPAT) || defined __banan_os__
|
||||
/* Copy from bionic/libc/private/arpa_nameser_compat.h
|
||||
* and bionic/libc/private/arpa_nameser.h */
|
||||
typedef struct {
|
||||
@@ -763,6 +767,14 @@
|
||||
#define dn_skipname __dn_skipname
|
||||
int dn_skipname(const u_char *, const u_char *);
|
||||
|
||||
+#if defined __banan_os__
|
||||
+#warning "TODO: dn_expand"
|
||||
+int dn_expand(const u_char *, const u_char *, const u_char *, char *, int)
|
||||
+{
|
||||
+ return -1;
|
||||
+}
|
||||
+#endif
|
||||
+
|
||||
/* From bionic/libc/private/arpa_nameser_compat.h */
|
||||
#define T_MX ns_t_mx
|
||||
#define T_TXT ns_t_txt
|
||||
@@ -1369,7 +1381,7 @@
|
||||
}
|
||||
|
||||
#if defined(G_OS_UNIX)
|
||||
-#ifdef __BIONIC__
|
||||
+#if defined __BIONIC__
|
||||
#ifndef C_IN
|
||||
#define C_IN 1
|
||||
#endif
|
||||
@@ -1420,6 +1432,9 @@
|
||||
g_byte_array_set_size (answer, len * 2);
|
||||
#if defined(HAVE_RES_NQUERY)
|
||||
len = res_nquery (&res, rrname, C_IN, rrtype, answer->data, answer->len);
|
||||
+#elif defined __banan_os__
|
||||
+#warning "TODO: res_query"
|
||||
+ len = -1;
|
||||
#else
|
||||
len = res_query (rrname, C_IN, rrtype, answer->data, answer->len);
|
||||
#endif
|
||||
diff -ruN glib-2.85.2/gio/meson.build glib-2.85.2-banan_os/gio/meson.build
|
||||
--- glib-2.85.2/gio/meson.build 2025-07-21 20:47:53.000000000 +0300
|
||||
+++ glib-2.85.2-banan_os/gio/meson.build 2025-08-19 18:21:06.062294634 +0300
|
||||
@@ -18,7 +18,7 @@
|
||||
|
||||
gnetworking_h_nameser_compat_include = ''
|
||||
|
||||
-if host_system not in ['windows', 'android']
|
||||
+if host_system not in ['windows', 'android', 'banan_os']
|
||||
# Don't check for C_IN on Android since it does not define it in public
|
||||
# headers, we define it ourselves wherever necessary
|
||||
if not cc.compiles('''#include <sys/types.h>
|
||||
@@ -40,6 +40,7 @@
|
||||
network_libs = [ ]
|
||||
network_args = [ ]
|
||||
if host_system != 'windows'
|
||||
+ if host_system != 'banan_os'
|
||||
# res_query()
|
||||
res_query_test = '''#include <resolv.h>
|
||||
int main (int argc, char ** argv) {
|
||||
@@ -63,6 +64,7 @@
|
||||
error('Could not find res_query()')
|
||||
endif
|
||||
endif
|
||||
+ endif
|
||||
|
||||
# socket()
|
||||
socket_test = '''#include <sys/types.h>
|
|
@ -1,39 +0,0 @@
|
|||
diff -ruN glib-2.85.2/gio/gunixmounts.c glib-2.85.2-banan_os/gio/gunixmounts.c
|
||||
--- glib-2.85.2/gio/gunixmounts.c 2025-07-21 20:47:53.000000000 +0300
|
||||
+++ glib-2.85.2-banan_os/gio/gunixmounts.c 2025-08-19 18:21:06.055332112 +0300
|
||||
@@ -1114,7 +1114,7 @@
|
||||
}
|
||||
|
||||
/* QNX {{{2 */
|
||||
-#elif defined (HAVE_QNX)
|
||||
+#elif defined (HAVE_QNX) || defined (__banan_os__)
|
||||
|
||||
static char *
|
||||
get_mtab_monitor_file (void)
|
||||
@@ -1754,6 +1754,26 @@
|
||||
if (time_read_out != NULL)
|
||||
*time_read_out = 0;
|
||||
if (n_points_out != NULL)
|
||||
+ *n_points_out = 0;
|
||||
+ return NULL;
|
||||
+}
|
||||
+
|
||||
+#elif defined (__banan_os__)
|
||||
+
|
||||
+static GList *
|
||||
+_g_get_unix_mount_points (void)
|
||||
+{
|
||||
+ return NULL;
|
||||
+}
|
||||
+
|
||||
+static GUnixMountPoint **
|
||||
+_g_unix_mount_points_get_from_file (const char *table_path,
|
||||
+ uint64_t *time_read_out,
|
||||
+ size_t *n_points_out)
|
||||
+{
|
||||
+ if (time_read_out != NULL)
|
||||
+ *time_read_out = 0;
|
||||
+ if (n_points_out != NULL)
|
||||
*n_points_out = 0;
|
||||
return NULL;
|
||||
}
|
|
@ -1,11 +0,0 @@
|
|||
#!/bin/bash ../install.sh
|
||||
|
||||
NAME='libffi'
|
||||
VERSION='3.5.2'
|
||||
DOWNLOAD_URL="https://github.com/libffi/libffi/releases/download/v$VERSION/libffi-$VERSION.tar.gz#f3a3082a23b37c293a4fcd1053147b371f2ff91fa7ea1b2a52e335676bac82dc"
|
||||
CONFIG_SUB=('config.sub')
|
||||
|
||||
post_install() {
|
||||
# remove libtool file
|
||||
rm -f $BANAN_SYSROOT/usr/lib/libffi.la
|
||||
}
|
|
@ -1,48 +0,0 @@
|
|||
diff -ruN libffi-3.5.2/configure libffi-3.5.2-banan_os/configure
|
||||
--- libffi-3.5.2/configure 2025-08-02 09:44:34.000000000 +0300
|
||||
+++ libffi-3.5.2-banan_os/configure 2025-08-08 18:24:29.271963294 +0300
|
||||
@@ -7432,6 +7432,10 @@
|
||||
lt_cv_deplibs_check_method=pass_all
|
||||
;;
|
||||
|
||||
+banan_os*)
|
||||
+ lt_cv_deplibs_check_method=pass_all
|
||||
+ ;;
|
||||
+
|
||||
beos*)
|
||||
lt_cv_deplibs_check_method=pass_all
|
||||
;;
|
||||
@@ -12978,6 +12982,16 @@
|
||||
esac
|
||||
;;
|
||||
|
||||
+banan_os*)
|
||||
+ version_type=linux # correct to gnu/linux during the next big refactor
|
||||
+ need_lib_prefix=no
|
||||
+ need_version=no
|
||||
+ library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'
|
||||
+ soname_spec='$libname$release$shared_ext$major'
|
||||
+ dynamic_linker="$host_os DynamicLoader.so"
|
||||
+ shlibpath_var=LD_LIBRARY_PATH
|
||||
+ ;;
|
||||
+
|
||||
beos*)
|
||||
library_names_spec='$libname$shared_ext'
|
||||
dynamic_linker="$host_os ld.so"
|
||||
@@ -17612,6 +17626,16 @@
|
||||
esac
|
||||
;;
|
||||
|
||||
+banan_os*)
|
||||
+ version_type=linux # correct to gnu/linux during the next big refactor
|
||||
+ need_lib_prefix=no
|
||||
+ need_version=no
|
||||
+ library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'
|
||||
+ soname_spec='$libname$release$shared_ext$major'
|
||||
+ dynamic_linker="$host_os DynamicLoader.so"
|
||||
+ shlibpath_var=LD_LIBRARY_PATH
|
||||
+ ;;
|
||||
+
|
||||
beos*)
|
||||
library_names_spec='$libname$shared_ext'
|
||||
dynamic_linker="$host_os ld.so"
|
|
@ -1,14 +0,0 @@
|
|||
#!/bin/bash ../install.sh
|
||||
|
||||
NAME='nano'
|
||||
VERSION='8.5'
|
||||
DOWNLOAD_URL="https://www.nano-editor.org/dist/v8/nano-$VERSION.tar.xz#000b011d339c141af9646d43288f54325ff5c6e8d39d6e482b787bbc6654c26a"
|
||||
DEPENDENCIES=('ncurses')
|
||||
CONFIG_SUB=('config.sub')
|
||||
CONFIGURE_OPTIONS=(
|
||||
'ac_cv_header_glob_h=no'
|
||||
)
|
||||
|
||||
pre_configure() {
|
||||
echo '#include_next <sys/types.h>' > lib/sys_types.in.h
|
||||
}
|
|
@ -1,21 +0,0 @@
|
|||
diff -ruN nano-8.5/lib/getprogname.c nano-8.5-banan_os/lib/getprogname.c
|
||||
--- nano-8.5/lib/getprogname.c 2025-06-12 10:29:39.000000000 +0300
|
||||
+++ nano-8.5-banan_os/lib/getprogname.c 2025-08-19 01:25:56.020428849 +0300
|
||||
@@ -50,7 +50,7 @@
|
||||
# include <sys/procfs.h>
|
||||
#endif
|
||||
|
||||
-#if defined __SCO_VERSION__ || defined __sysv5__
|
||||
+#if defined __SCO_VERSION__ || defined __sysv5__ || defined __banan_os__
|
||||
# include <fcntl.h>
|
||||
# include <string.h>
|
||||
#endif
|
||||
@@ -265,7 +265,7 @@
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
-# elif defined __SCO_VERSION__ || defined __sysv5__ /* SCO OpenServer6/UnixWare */
|
||||
+# elif defined __SCO_VERSION__ || defined __sysv5__ || defined __banan_os__ /* SCO OpenServer6/UnixWare */
|
||||
char buf[80];
|
||||
int fd;
|
||||
sprintf (buf, "/proc/%d/cmdline", getpid());
|
|
@ -1,13 +0,0 @@
|
|||
#!/bin/bash ../install.sh
|
||||
|
||||
NAME='nyancat'
|
||||
VERSION='git'
|
||||
DOWNLOAD_URL="https://github.com/klange/nyancat.git#1.5.2"
|
||||
|
||||
configure() {
|
||||
:
|
||||
}
|
||||
|
||||
install() {
|
||||
cp src/nyancat "$BANAN_SYSROOT/usr/bin/"
|
||||
}
|
|
@ -1,12 +0,0 @@
|
|||
#!/bin/bash ../install.sh
|
||||
|
||||
NAME='pcre2'
|
||||
VERSION='10.45'
|
||||
DOWNLOAD_URL="https://github.com/PCRE2Project/pcre2/releases/download/pcre2-$VERSION/pcre2-$VERSION.tar.gz#0e138387df7835d7403b8351e2226c1377da804e0737db0e071b48f07c9d12ee"
|
||||
CONFIG_SUB=('config.sub')
|
||||
|
||||
post_install() {
|
||||
# remove libtool files
|
||||
rm -f $BANAN_SYSROOT/usr/lib/libpcre2-8.la
|
||||
rm -f $BANAN_SYSROOT/usr/lib/libpcre2-posix.la
|
||||
}
|
|
@ -1,31 +0,0 @@
|
|||
diff -ruN pcre2-10.45/configure pcre2-10.45-banan_os/configure
|
||||
--- pcre2-10.45/configure 2025-02-04 15:48:33.000000000 +0200
|
||||
+++ pcre2-10.45-banan_os/configure 2025-08-08 00:22:52.975889591 +0300
|
||||
@@ -6536,6 +6536,10 @@
|
||||
lt_cv_deplibs_check_method=pass_all
|
||||
;;
|
||||
|
||||
+banan_os*)
|
||||
+ lt_cv_deplibs_check_method=pass_all
|
||||
+ ;;
|
||||
+
|
||||
beos*)
|
||||
lt_cv_deplibs_check_method=pass_all
|
||||
;;
|
||||
@@ -12197,6 +12201,16 @@
|
||||
esac
|
||||
;;
|
||||
|
||||
+banan_os*)
|
||||
+ version_type=linux # correct to gnu/linux during the next big refactor
|
||||
+ need_lib_prefix=no
|
||||
+ need_version=no
|
||||
+ library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'
|
||||
+ soname_spec='$libname$release$shared_ext$major'
|
||||
+ dynamic_linker="$host_os DynamicLoader.so"
|
||||
+ shlibpath_var=LD_LIBRARY_PATH
|
||||
+ ;;
|
||||
+
|
||||
beos*)
|
||||
library_names_spec='$libname$shared_ext'
|
||||
dynamic_linker="$host_os ld.so"
|
|
@ -1,17 +0,0 @@
|
|||
#!/bin/bash ../install.sh
|
||||
|
||||
NAME='qemu'
|
||||
VERSION='10.0.2'
|
||||
DOWNLOAD_URL="https://download.qemu.org/qemu-$VERSION.tar.xz#ef786f2398cb5184600f69aef4d5d691efd44576a3cff4126d38d4c6fec87759"
|
||||
DEPENDENCIES=('glib' 'SDL2')
|
||||
MAKE_BUILD_TARGETS=('qemu-system-x86_64')
|
||||
CONFIGURE_OPTIONS=(
|
||||
'--cross-prefix='
|
||||
'--target-list=x86_64-softmmu'
|
||||
'--disable-tpm'
|
||||
'--disable-docs'
|
||||
)
|
||||
|
||||
pre_configure() {
|
||||
echo '' > tests/meson.build
|
||||
}
|
|
@ -1,12 +0,0 @@
|
|||
diff -ruN qemu-10.0.2/configure qemu-10.0.2-banan_os/configure
|
||||
--- qemu-10.0.2/configure 2025-05-29 01:05:46.000000000 +0300
|
||||
+++ qemu-10.0.2-banan_os/configure 2025-05-31 00:03:10.361102831 +0300
|
||||
@@ -360,6 +360,8 @@
|
||||
host_os=netbsd
|
||||
elif check_define __APPLE__; then
|
||||
host_os=darwin
|
||||
+elif check_define __banan_os__; then
|
||||
+ host_os=banan_os
|
||||
else
|
||||
# This is a fatal error, but don't report it yet, because we
|
||||
# might be going to just print the --help text, or it might
|
|
@ -1,43 +0,0 @@
|
|||
diff -ru qemu-10.0.2/util/oslib-posix.c qemu-10.0.2-x86_64/util/oslib-posix.c
|
||||
--- qemu-10.0.2/util/oslib-posix.c 2025-05-29 01:05:47.000000000 +0300
|
||||
+++ qemu-10.0.2-x86_64/util/oslib-posix.c 2025-08-18 02:38:04.839116456 +0300
|
||||
@@ -128,7 +128,39 @@
|
||||
|
||||
int qemu_daemon(int nochdir, int noclose)
|
||||
{
|
||||
+#if defined(__banan_os__)
|
||||
+ const pid_t pid = fork();
|
||||
+ if (pid == -1) {
|
||||
+ return -1;
|
||||
+ }
|
||||
+ if (pid > 0) {
|
||||
+ exit(0);
|
||||
+ }
|
||||
+
|
||||
+ if (setsid() == -1) {
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ if (nochdir == 0) {
|
||||
+ if (chdir("/") == -1) {
|
||||
+ return -1;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (noclose == 0) {
|
||||
+ int fd = open("/dev/null", O_RDWR);
|
||||
+ if (fd == -1) {
|
||||
+ return -1;
|
||||
+ }
|
||||
+ dup2(fd, STDIN_FILENO);
|
||||
+ dup2(fd, STDOUT_FILENO);
|
||||
+ dup2(fd, STDERR_FILENO);
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
+#else
|
||||
return daemon(nochdir, noclose);
|
||||
+#endif
|
||||
}
|
||||
|
||||
bool qemu_write_pidfile(const char *path, Error **errp)
|
|
@ -1,24 +0,0 @@
|
|||
diff -ru qemu-10.0.2/util/main-loop.c qemu-10.0.2-x86_64/util/main-loop.c
|
||||
--- qemu-10.0.2/util/main-loop.c 2025-05-29 01:05:47.000000000 +0300
|
||||
+++ qemu-10.0.2-x86_64/util/main-loop.c 2025-08-09 18:35:25.670990547 +0300
|
||||
@@ -95,8 +95,10 @@
|
||||
* not catch it reliably.
|
||||
*/
|
||||
sigemptyset(&set);
|
||||
+#if !defined(__banan_os__)
|
||||
sigaddset(&set, SIG_IPI);
|
||||
sigaddset(&set, SIGIO);
|
||||
+#endif
|
||||
sigaddset(&set, SIGALRM);
|
||||
sigaddset(&set, SIGBUS);
|
||||
/* SIGINT cannot be handled via signalfd, so that ^C can be used
|
||||
@@ -106,7 +108,9 @@
|
||||
*/
|
||||
pthread_sigmask(SIG_BLOCK, &set, NULL);
|
||||
|
||||
+#if !defined(__banan_os__)
|
||||
sigdelset(&set, SIG_IPI);
|
||||
+#endif
|
||||
sigfd = qemu_signalfd(&set);
|
||||
if (sigfd == -1) {
|
||||
error_setg_errno(errp, errno, "failed to create signalfd");
|
|
@ -1,22 +0,0 @@
|
|||
diff -ru qemu-10.0.2/net/colo.c qemu-10.0.2-x86_64/net/colo.c
|
||||
--- qemu-10.0.2/net/colo.c 2025-05-29 01:05:46.000000000 +0300
|
||||
+++ qemu-10.0.2-x86_64/net/colo.c 2025-08-09 19:24:57.624758915 +0300
|
||||
@@ -123,14 +123,18 @@
|
||||
case IPPROTO_TCP:
|
||||
case IPPROTO_UDP:
|
||||
case IPPROTO_DCCP:
|
||||
+#if !defined(__banan_os__)
|
||||
case IPPROTO_ESP:
|
||||
+#endif
|
||||
case IPPROTO_SCTP:
|
||||
case IPPROTO_UDPLITE:
|
||||
tmp_ports = *(uint32_t *)(pkt->transport_header);
|
||||
break;
|
||||
+#if !defined(__banan_os__)
|
||||
case IPPROTO_AH:
|
||||
tmp_ports = *(uint32_t *)(pkt->transport_header + 4);
|
||||
break;
|
||||
+#endif
|
||||
default:
|
||||
break;
|
||||
}
|
|
@ -1,32 +0,0 @@
|
|||
diff -ru qemu-10.0.2/block/file-posix.c qemu-10.0.2-x86_64/block/file-posix.c
|
||||
--- qemu-10.0.2/block/file-posix.c 2025-05-29 01:05:46.000000000 +0300
|
||||
+++ qemu-10.0.2-x86_64/block/file-posix.c 2025-08-09 19:00:18.062695074 +0300
|
||||
@@ -110,6 +110,10 @@
|
||||
#include <sys/diskslice.h>
|
||||
#endif
|
||||
|
||||
+#ifdef __banan_os__
|
||||
+#include <sys/ioctl.h>
|
||||
+#endif
|
||||
+
|
||||
/* OS X does not have O_DSYNC */
|
||||
#ifndef O_DSYNC
|
||||
#ifdef O_SYNC
|
||||
Only in qemu-10.0.2-x86_64: build
|
||||
Only in qemu-10.0.2-x86_64: .cache
|
||||
diff -ru qemu-10.0.2/chardev/char-pty.c qemu-10.0.2-x86_64/chardev/char-pty.c
|
||||
--- qemu-10.0.2/chardev/char-pty.c 2025-05-29 01:05:46.000000000 +0300
|
||||
+++ qemu-10.0.2-x86_64/chardev/char-pty.c 2025-08-09 19:03:07.909515897 +0300
|
||||
@@ -236,7 +236,11 @@
|
||||
# include <termios.h>
|
||||
#endif
|
||||
|
||||
-#ifdef __sun__
|
||||
+#if defined(__banan_os__)
|
||||
+# include <sys/ioctl.h>
|
||||
+#endif
|
||||
+
|
||||
+#if defined(__sun__) || defined(__banan_os__)
|
||||
|
||||
#if !defined(HAVE_OPENPTY)
|
||||
/* Once illumos has openpty(), this is going to be removed. */
|
|
@ -19,6 +19,7 @@ setjmp:
|
|||
xorl %eax, %eax
|
||||
|
||||
ret
|
||||
|
||||
.size setjmp, . - setjmp
|
||||
|
||||
// void longjmp(jmp_buf env, int val)
|
||||
|
@ -38,27 +39,5 @@ longjmp:
|
|||
movl 16(%edx), %edi
|
||||
movl 20(%edx), %esi
|
||||
jmp *%ecx
|
||||
|
||||
.size longjmp, . - longjmp
|
||||
|
||||
// int sigsetjmp(sigjmp_buf env, int savemask)
|
||||
.global sigsetjmp
|
||||
sigsetjmp:
|
||||
movl 4(%esp), %edx
|
||||
movl 8(%esp), %ecx
|
||||
|
||||
movl %ecx, 24(%edx)
|
||||
testl %ecx, %ecx
|
||||
jz setjmp
|
||||
|
||||
leal 24(%edx), %edx
|
||||
xorl %ecx, %ecx
|
||||
|
||||
subl $12, %esp
|
||||
movl %edx, 8(%esp)
|
||||
movl %ecx, 4(%esp)
|
||||
movl %ecx, 0(%esp)
|
||||
call pthread_sigmask
|
||||
addl $12, %esp
|
||||
|
||||
jmp setjmp
|
||||
.size sigsetjmp, . - sigsetjmp
|
||||
|
|
|
@ -38,21 +38,3 @@ longjmp:
|
|||
movq 56(%rdi), %r15
|
||||
jmp *%rcx
|
||||
.size longjmp, . - longjmp
|
||||
|
||||
// int sigsetjmp(sigjmp_buf env, int savemask)
|
||||
.global sigsetjmp
|
||||
sigsetjmp:
|
||||
movq %rsi, 64(%rdi)
|
||||
testq %rsi, %rsi
|
||||
jz setjmp
|
||||
|
||||
subq $8, %rsp
|
||||
movq %rdi, (%rsp)
|
||||
leaq 72(%rsi), %rdx
|
||||
xorq %rsi, %rsi
|
||||
call pthread_sigmask
|
||||
movq (%rsp), %rdi
|
||||
addq $8, %rsp
|
||||
|
||||
jmp setjmp
|
||||
.size sigsetjmp, . - sigsetjmp
|
||||
|
|
|
@ -1,13 +1,5 @@
|
|||
#include <dlfcn.h>
|
||||
|
||||
extern "C" int __dladdr(const void*, Dl_info_t*) __attribute__((weak));
|
||||
int dladdr(const void* __restrict addr, Dl_info_t* __restrict dlip)
|
||||
{
|
||||
if (&__dladdr == nullptr) [[unlikely]]
|
||||
return 0;
|
||||
return __dladdr(addr, dlip);
|
||||
}
|
||||
|
||||
extern "C" int __dlclose(void*) __attribute__((weak));
|
||||
int dlclose(void* handle)
|
||||
{
|
||||
|
|
|
@ -26,8 +26,7 @@ typedef struct
|
|||
typedef struct
|
||||
{
|
||||
pthread_mutexattr_t attr;
|
||||
uint32_t futex;
|
||||
uint32_t waiters;
|
||||
pthread_t locker;
|
||||
unsigned lock_depth;
|
||||
} pthread_mutex_t;
|
||||
|
||||
|
|
|
@ -15,18 +15,6 @@ __BEGIN_DECLS
|
|||
#define RTLD_NEXT ((void*)-1)
|
||||
#define RTLD_DEFAULT ((void*) 0)
|
||||
|
||||
struct Dl_info
|
||||
{
|
||||
const char* dli_fname; /* Pathname of mapped object file. */
|
||||
void* dli_fbase; /* Base of mapped address range. */
|
||||
const char* dli_sname; /* Sumbol name or null pointer. */
|
||||
void* dli_saddr; /* Symbol address or null pointer. */
|
||||
};
|
||||
|
||||
typedef struct Dl_info Dl_info_t; /* POSIX type */
|
||||
typedef struct Dl_info Dl_info; /* Linux type */
|
||||
|
||||
int dladdr(const void* __restrict addr, Dl_info_t* __restrict dlip);
|
||||
int dlclose(void* handle);
|
||||
char* dlerror(void);
|
||||
void* dlopen(const char* file, int mode);
|
||||
|
|
|
@ -79,7 +79,7 @@ struct uthread
|
|||
|
||||
#define PTHREAD_SPIN_INITIALIZER (pthread_spinlock_t)0
|
||||
#define PTHREAD_COND_INITIALIZER (pthread_cond_t){ { CLOCK_REALTIME, 0 }, PTHREAD_SPIN_INITIALIZER, NULL }
|
||||
#define PTHREAD_MUTEX_INITIALIZER (pthread_mutex_t){ { PTHREAD_MUTEX_DEFAULT, 0 }, 0, 0, 0 }
|
||||
#define PTHREAD_MUTEX_INITIALIZER (pthread_mutex_t){ { PTHREAD_MUTEX_DEFAULT, 0 }, 0, 0 }
|
||||
#define PTHREAD_RWLOCK_INITIALIZER (pthread_rwlock_t){ { 0 }, 0, 0 }
|
||||
|
||||
#define _PTHREAD_ATFORK_PREPARE 0
|
||||
|
|
|
@ -132,9 +132,8 @@ struct sigevent
|
|||
#define SA_SIGINFO 0x010
|
||||
#define SA_NOCLDWAIT 0x020
|
||||
#define SA_NODEFER 0x040
|
||||
|
||||
#define SS_ONSTACK 1
|
||||
#define SS_DISABLE 2
|
||||
#define SS_ONSTACK 0x080
|
||||
#define SS_DISABLE 0x100
|
||||
|
||||
#define MINSIGSTKSZ 4096
|
||||
#define SIGSTKSZ 4096
|
||||
|
|
|
@ -90,9 +90,6 @@ __BEGIN_DECLS
|
|||
O(SYS_SIGACTION, sigaction) \
|
||||
O(SYS_SIGPENDING, sigpending) \
|
||||
O(SYS_SIGPROCMASK, sigprocmask) \
|
||||
O(SYS_SIGSUSPEND, sigsuspend) \
|
||||
O(SYS_SIGWAIT, sigwait) \
|
||||
O(SYS_SIGALTSTACK, sigaltstack) \
|
||||
O(SYS_SETITIMER, setitimer) \
|
||||
O(SYS_POSIX_OPENPT, posix_openpt) \
|
||||
O(SYS_PTSNAME, ptsname) \
|
||||
|
|
|
@ -146,7 +146,7 @@ __BEGIN_DECLS
|
|||
|
||||
#if !defined(__time_t_defined) && (defined(__need_all_types) || defined(__need_time_t))
|
||||
#define __time_t_defined 1
|
||||
typedef long long time_t;
|
||||
typedef unsigned long long time_t;
|
||||
#endif
|
||||
#undef __need_time_t
|
||||
|
||||
|
|
|
@ -17,7 +17,7 @@ __BEGIN_DECLS
|
|||
|
||||
#include <bits/types/locale_t.h>
|
||||
|
||||
typedef int mbstate_t;
|
||||
typedef struct {} mbstate_t;
|
||||
|
||||
typedef int wctype_t;
|
||||
|
||||
|
|
|
@ -736,6 +736,34 @@ int pthread_spin_unlock(pthread_spinlock_t* lock)
|
|||
return 0;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
static int _pthread_timedlock(T* __restrict lock, const struct timespec* __restrict abstime, int (*trylock)(T*))
|
||||
{
|
||||
if (trylock(lock) == 0)
|
||||
return 0;
|
||||
|
||||
constexpr auto has_timed_out =
|
||||
[](const struct timespec* abstime) -> bool
|
||||
{
|
||||
struct timespec curtime;
|
||||
clock_gettime(CLOCK_REALTIME, &curtime);
|
||||
if (curtime.tv_sec < abstime->tv_sec)
|
||||
return false;
|
||||
if (curtime.tv_sec > abstime->tv_sec)
|
||||
return true;
|
||||
return curtime.tv_nsec >= abstime->tv_nsec;
|
||||
};
|
||||
|
||||
while (!has_timed_out(abstime))
|
||||
{
|
||||
if (trylock(lock) == 0)
|
||||
return 0;
|
||||
sched_yield();
|
||||
}
|
||||
|
||||
return ETIMEDOUT;
|
||||
}
|
||||
|
||||
int pthread_mutexattr_destroy(pthread_mutexattr_t* attr)
|
||||
{
|
||||
(void)attr;
|
||||
|
@ -807,8 +835,7 @@ int pthread_mutex_init(pthread_mutex_t* __restrict mutex, const pthread_mutexatt
|
|||
attr = &default_attr;
|
||||
*mutex = {
|
||||
.attr = *attr,
|
||||
.futex = 0,
|
||||
.waiters = 0,
|
||||
.locker = 0,
|
||||
.lock_depth = 0,
|
||||
};
|
||||
return 0;
|
||||
|
@ -816,28 +843,55 @@ int pthread_mutex_init(pthread_mutex_t* __restrict mutex, const pthread_mutexatt
|
|||
|
||||
int pthread_mutex_lock(pthread_mutex_t* mutex)
|
||||
{
|
||||
return pthread_mutex_timedlock(mutex, nullptr);
|
||||
}
|
||||
// NOTE: current yielding implementation supports shared
|
||||
|
||||
int pthread_mutex_trylock(pthread_mutex_t* mutex)
|
||||
{
|
||||
const uint32_t tid = pthread_self();
|
||||
const auto tid = pthread_self();
|
||||
|
||||
switch (mutex->attr.type)
|
||||
{
|
||||
case PTHREAD_MUTEX_RECURSIVE:
|
||||
if (mutex->futex != tid)
|
||||
if (mutex->locker != tid)
|
||||
break;
|
||||
mutex->lock_depth++;
|
||||
return 0;
|
||||
case PTHREAD_MUTEX_ERRORCHECK:
|
||||
if (mutex->futex != tid)
|
||||
if (mutex->locker != tid)
|
||||
break;
|
||||
return EDEADLK;
|
||||
}
|
||||
|
||||
uint32_t expected = 0;
|
||||
if (!BAN::atomic_compare_exchange(mutex->futex, expected, tid, BAN::MemoryOrder::memory_order_acquire))
|
||||
pthread_t expected = 0;
|
||||
while (!BAN::atomic_compare_exchange(mutex->locker, expected, tid, BAN::MemoryOrder::memory_order_acquire))
|
||||
{
|
||||
sched_yield();
|
||||
expected = 0;
|
||||
}
|
||||
|
||||
mutex->lock_depth = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pthread_mutex_trylock(pthread_mutex_t* mutex)
|
||||
{
|
||||
// NOTE: current yielding implementation supports shared
|
||||
|
||||
const auto tid = pthread_self();
|
||||
|
||||
switch (mutex->attr.type)
|
||||
{
|
||||
case PTHREAD_MUTEX_RECURSIVE:
|
||||
if (mutex->locker != tid)
|
||||
break;
|
||||
mutex->lock_depth++;
|
||||
return 0;
|
||||
case PTHREAD_MUTEX_ERRORCHECK:
|
||||
if (mutex->locker != tid)
|
||||
break;
|
||||
return EDEADLK;
|
||||
}
|
||||
|
||||
pthread_t expected = 0;
|
||||
if (!BAN::atomic_compare_exchange(mutex->locker, expected, tid, BAN::MemoryOrder::memory_order_acquire))
|
||||
return EBUSY;
|
||||
|
||||
mutex->lock_depth = 1;
|
||||
|
@ -846,42 +900,18 @@ int pthread_mutex_trylock(pthread_mutex_t* mutex)
|
|||
|
||||
int pthread_mutex_timedlock(pthread_mutex_t* __restrict mutex, const struct timespec* __restrict abstime)
|
||||
{
|
||||
// recursive/errorcheck handled in trylock to remove code duplication
|
||||
if (const int ret = pthread_mutex_trylock(mutex); ret != EBUSY)
|
||||
return ret;
|
||||
|
||||
const uint32_t tid = pthread_self();
|
||||
|
||||
uint32_t expected = 0;
|
||||
while (!BAN::atomic_compare_exchange(mutex->futex, expected, tid, BAN::memory_order_acquire))
|
||||
{
|
||||
const int op = FUTEX_WAIT | (mutex->attr.shared ? 0 : FUTEX_PRIVATE) | FUTEX_REALTIME;
|
||||
|
||||
BAN::atomic_add_fetch(mutex->waiters, 1);
|
||||
const auto ret = futex(op, &mutex->futex, expected, abstime);
|
||||
BAN::atomic_sub_fetch(mutex->waiters, 1);
|
||||
|
||||
if (ret == -1 && errno == ETIMEDOUT)
|
||||
return ETIMEDOUT;
|
||||
|
||||
expected = 0;
|
||||
}
|
||||
|
||||
mutex->lock_depth = 1;
|
||||
return 0;
|
||||
return _pthread_timedlock(mutex, abstime, &pthread_mutex_trylock);
|
||||
}
|
||||
|
||||
int pthread_mutex_unlock(pthread_mutex_t* mutex)
|
||||
{
|
||||
ASSERT(mutex->futex == static_cast<uint32_t>(pthread_self()));
|
||||
// NOTE: current yielding implementation supports shared
|
||||
|
||||
ASSERT(mutex->locker == pthread_self());
|
||||
|
||||
mutex->lock_depth--;
|
||||
if (mutex->lock_depth == 0)
|
||||
{
|
||||
BAN::atomic_store(mutex->futex, 0, BAN::memory_order_release);
|
||||
if (BAN::atomic_load(mutex->waiters))
|
||||
futex(FUTEX_WAKE, &mutex->futex, 1, nullptr);
|
||||
}
|
||||
BAN::atomic_store(mutex->locker, 0, BAN::MemoryOrder::memory_order_release);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -941,36 +971,6 @@ int pthread_rwlock_init(pthread_rwlock_t* __restrict rwlock, const pthread_rwloc
|
|||
return 0;
|
||||
}
|
||||
|
||||
// TODO: rewrite rwlock with futexes
|
||||
|
||||
template<typename T>
|
||||
static int pthread_rwlock_timedlock(T* __restrict lock, const struct timespec* __restrict abstime, int (*trylock)(T*))
|
||||
{
|
||||
if (trylock(lock) == 0)
|
||||
return 0;
|
||||
|
||||
constexpr auto has_timed_out =
|
||||
[](const struct timespec* abstime) -> bool
|
||||
{
|
||||
struct timespec curtime;
|
||||
clock_gettime(CLOCK_REALTIME, &curtime);
|
||||
if (curtime.tv_sec < abstime->tv_sec)
|
||||
return false;
|
||||
if (curtime.tv_sec > abstime->tv_sec)
|
||||
return true;
|
||||
return curtime.tv_nsec >= abstime->tv_nsec;
|
||||
};
|
||||
|
||||
while (!has_timed_out(abstime))
|
||||
{
|
||||
if (trylock(lock) == 0)
|
||||
return 0;
|
||||
sched_yield();
|
||||
}
|
||||
|
||||
return ETIMEDOUT;
|
||||
}
|
||||
|
||||
int pthread_rwlock_rdlock(pthread_rwlock_t* rwlock)
|
||||
{
|
||||
unsigned expected = BAN::atomic_load(rwlock->lockers);
|
||||
|
@ -995,7 +995,7 @@ int pthread_rwlock_tryrdlock(pthread_rwlock_t* rwlock)
|
|||
|
||||
int pthread_rwlock_timedrdlock(pthread_rwlock_t* __restrict rwlock, const struct timespec* __restrict abstime)
|
||||
{
|
||||
return pthread_rwlock_timedlock(rwlock, abstime, &pthread_rwlock_tryrdlock);
|
||||
return _pthread_timedlock(rwlock, abstime, &pthread_rwlock_tryrdlock);
|
||||
}
|
||||
|
||||
int pthread_rwlock_wrlock(pthread_rwlock_t* rwlock)
|
||||
|
@ -1021,7 +1021,7 @@ int pthread_rwlock_trywrlock(pthread_rwlock_t* rwlock)
|
|||
|
||||
int pthread_rwlock_timedwrlock(pthread_rwlock_t* __restrict rwlock, const struct timespec* __restrict abstime)
|
||||
{
|
||||
return pthread_rwlock_timedlock(rwlock, abstime, &pthread_rwlock_trywrlock);
|
||||
return _pthread_timedlock(rwlock, abstime, &pthread_rwlock_trywrlock);
|
||||
}
|
||||
|
||||
int pthread_rwlock_unlock(pthread_rwlock_t* rwlock)
|
||||
|
|
|
@ -7,5 +7,13 @@ void siglongjmp(sigjmp_buf env, int val)
|
|||
{
|
||||
if (env[_JMP_BUF_REGS])
|
||||
pthread_sigmask(SIG_SETMASK, reinterpret_cast<sigset_t*>(&env[_JMP_BUF_REGS + 1]), nullptr);
|
||||
longjmp(env, val);
|
||||
return longjmp(env, val);
|
||||
}
|
||||
|
||||
int sigsetjmp(sigjmp_buf env, int savemask)
|
||||
{
|
||||
env[_JMP_BUF_REGS] = savemask;
|
||||
if (savemask)
|
||||
pthread_sigmask(0, nullptr, reinterpret_cast<sigset_t*>(&env[_JMP_BUF_REGS + 1]));
|
||||
return setjmp(env);
|
||||
}
|
||||
|
|
|
@ -164,22 +164,3 @@ int sigrelse(int sig)
|
|||
(void)sigaddset(&set, sig);
|
||||
return sigprocmask(SIG_UNBLOCK, &set, nullptr);
|
||||
}
|
||||
|
||||
int sigsuspend(const sigset_t* sigmask)
|
||||
{
|
||||
return syscall(SYS_SIGSUSPEND, sigmask);
|
||||
}
|
||||
|
||||
int sigwait(const sigset_t* __restrict set, int* __restrict sig)
|
||||
{
|
||||
if (syscall(SYS_SIGWAIT, set, sig) == -1)
|
||||
return errno;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int sigaltstack(const stack_t* __restrict ss, stack_t* __restrict oss)
|
||||
{
|
||||
if (syscall(SYS_SIGALTSTACK, ss, oss) == -1)
|
||||
return errno;
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -606,7 +606,6 @@ int mbtowc(wchar_t* __restrict pwc, const char* __restrict s, size_t n)
|
|||
|
||||
return wch ? length : 0;
|
||||
}
|
||||
|
||||
ASSERT_NOT_REACHED();
|
||||
}
|
||||
|
||||
|
@ -646,31 +645,6 @@ size_t mbstowcs(wchar_t* __restrict pwcs, const char* __restrict s, size_t n)
|
|||
return written;
|
||||
}
|
||||
|
||||
int wctomb(char* s, wchar_t wchar)
|
||||
{
|
||||
// no state-dependent encodings
|
||||
if (s == nullptr)
|
||||
return 0;
|
||||
|
||||
switch (__getlocale(LC_CTYPE))
|
||||
{
|
||||
case locale_t::LOCALE_INVALID:
|
||||
ASSERT_NOT_REACHED();
|
||||
case locale_t::LOCALE_POSIX:
|
||||
*s = wchar;
|
||||
return wchar ? 1 : 0;
|
||||
case locale_t::LOCALE_UTF8:
|
||||
char buffer[5];
|
||||
if (!BAN::UTF8::from_codepoints(&wchar, 1, buffer))
|
||||
return -1;
|
||||
const size_t length = strlen(buffer);
|
||||
memcpy(s, buffer, length);
|
||||
return length;
|
||||
}
|
||||
|
||||
ASSERT_NOT_REACHED();
|
||||
}
|
||||
|
||||
size_t wcstombs(char* __restrict s, const wchar_t* __restrict pwcs, size_t n)
|
||||
{
|
||||
size_t written = 0;
|
||||
|
|
|
@ -1,4 +1,3 @@
|
|||
#include <BAN/Assert.h>
|
||||
#include <BAN/Debug.h>
|
||||
#include <BAN/Math.h>
|
||||
|
||||
|
@ -168,18 +167,15 @@ time_t mktime(struct tm* tm)
|
|||
|
||||
struct tm* gmtime_r(const time_t* timer, struct tm* __restrict result)
|
||||
{
|
||||
// FIXME: allow negative times :)
|
||||
ASSERT(*timer >= 0);
|
||||
|
||||
constexpr uint64_t month_days[] { 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365 };
|
||||
|
||||
unsigned long long time = *timer;
|
||||
time_t time = *timer;
|
||||
|
||||
result->tm_sec = time % 60; time /= 60;
|
||||
result->tm_min = time % 60; time /= 60;
|
||||
result->tm_hour = time % 24; time /= 24;
|
||||
|
||||
unsigned long long total_days = time;
|
||||
time_t total_days = time;
|
||||
result->tm_wday = (total_days + 4) % 7;
|
||||
result->tm_year = 1970;
|
||||
while (total_days >= 365U + is_leap_year(result->tm_year))
|
||||
|
|
|
@ -335,10 +335,6 @@ namespace LibGUI
|
|||
if (m_window_shown_event_callback)
|
||||
m_window_shown_event_callback(TRY_OR_BREAK(EventPacket::WindowShownEvent::deserialize(packet_data.span())).event);
|
||||
break;
|
||||
case PacketType::WindowFocusEvent:
|
||||
if (m_window_focus_event_callback)
|
||||
m_window_focus_event_callback(TRY_OR_BREAK(EventPacket::WindowFocusEvent::deserialize(packet_data.span())).event);
|
||||
break;
|
||||
case PacketType::KeyEvent:
|
||||
if (m_key_event_callback)
|
||||
m_key_event_callback(TRY_OR_BREAK(EventPacket::KeyEvent::deserialize(packet_data.span())).event);
|
||||
|
|
|
@ -217,7 +217,6 @@ namespace LibGUI
|
|||
CloseWindowEvent,
|
||||
ResizeWindowEvent,
|
||||
WindowShownEvent,
|
||||
WindowFocusEvent,
|
||||
KeyEvent,
|
||||
MouseButtonEvent,
|
||||
MouseMoveEvent,
|
||||
|
@ -334,14 +333,6 @@ namespace LibGUI
|
|||
event_t, event
|
||||
);
|
||||
|
||||
DEFINE_PACKET_EXTRA(
|
||||
WindowFocusEvent,
|
||||
struct event_t {
|
||||
bool focused;
|
||||
},
|
||||
event_t, event
|
||||
);
|
||||
|
||||
DEFINE_PACKET_EXTRA(
|
||||
KeyEvent,
|
||||
using event_t = LibInput::KeyEvent,
|
||||
|
|
|
@ -76,7 +76,6 @@ namespace LibGUI
|
|||
void set_mouse_move_event_callback(BAN::Function<void(EventPacket::MouseMoveEvent::event_t)> callback) { m_mouse_move_event_callback = callback; }
|
||||
void set_mouse_scroll_event_callback(BAN::Function<void(EventPacket::MouseScrollEvent::event_t)> callback) { m_mouse_scroll_event_callback = callback; }
|
||||
void set_window_shown_event_callback(BAN::Function<void(EventPacket::WindowShownEvent::event_t)> callback) { m_window_shown_event_callback = callback; }
|
||||
void set_window_focus_event_callback(BAN::Function<void(EventPacket::WindowFocusEvent::event_t)> callback) { m_window_focus_event_callback = callback; }
|
||||
|
||||
int server_fd() const { return m_server_fd; }
|
||||
|
||||
|
@ -109,7 +108,6 @@ namespace LibGUI
|
|||
BAN::Function<void()> m_close_window_event_callback;
|
||||
BAN::Function<void()> m_resize_window_event_callback;
|
||||
BAN::Function<void(EventPacket::WindowShownEvent::event_t)> m_window_shown_event_callback;
|
||||
BAN::Function<void(EventPacket::WindowFocusEvent::event_t)> m_window_focus_event_callback;
|
||||
BAN::Function<void(EventPacket::KeyEvent::event_t)> m_key_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseButtonEvent::event_t)> m_mouse_button_event_callback;
|
||||
BAN::Function<void(EventPacket::MouseMoveEvent::event_t)> m_mouse_move_event_callback;
|
||||
|
|
|
@ -58,7 +58,7 @@ namespace LibInput
|
|||
"å", "ä", "ö",
|
||||
"0", "1", "2", "3", "4", "5", "6", "7", "8", "9",
|
||||
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr,
|
||||
/*"Insert", "PrintScreen", "Delete", "Home", "End", "PageUp", "PageDown",*/ nullptr, nullptr, "\x7F", nullptr, nullptr, nullptr, nullptr, "\r", " ",
|
||||
/*"Insert", "PrintScreen", "Delete", "Home", "End", "PageUp", "PageDown",*/ nullptr, nullptr, "\x7F", nullptr, nullptr, nullptr, nullptr, "\n", " ",
|
||||
"!", "\"", "#", "¤", "%", "&", "/", "§", "½",
|
||||
"(", ")", "[", "]", "{", "}",
|
||||
"=", "?", "+", "\\", "´", "`", "¨", "¸", "\b", "@", "£", "$", "€",
|
||||
|
@ -77,7 +77,7 @@ namespace LibInput
|
|||
"Å", "Ä", "Ö",
|
||||
"0", "1", "2", "3", "4", "5", "6", "7", "8", "9",
|
||||
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr,
|
||||
/*"Insert", "PrintScreen", "Delete", "Home", "End", "PageUp", "PageDown",*/ nullptr, nullptr, "\x7F", nullptr, nullptr, nullptr, nullptr, "\r", " ",
|
||||
/*"Insert", "PrintScreen", "Delete", "Home", "End", "PageUp", "PageDown",*/ nullptr, nullptr, "\x7F", nullptr, nullptr, nullptr, nullptr, "\n", " ",
|
||||
"!", "\"", "#", "¤", "%", "&", "/", "§", "½",
|
||||
"(", ")", "[", "]", "{", "}",
|
||||
"=", "?", "+", "\\", "´", "`", "¨", "¸", "\b", "@", "£", "$", "€",
|
||||
|
@ -96,7 +96,7 @@ namespace LibInput
|
|||
"Å", "Ä", "Ö",
|
||||
"0", "1", "2", "3", "4", "5", "6", "7", "8", "9",
|
||||
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr,
|
||||
/*"Insert", "PrintScreen", "Delete", "Home", "End", "PageUp", "PageDown",*/ nullptr, nullptr, "\x7F", nullptr, nullptr, nullptr, nullptr, "\r", " ",
|
||||
/*"Insert", "PrintScreen", "Delete", "Home", "End", "PageUp", "PageDown",*/ nullptr, nullptr, "\x7F", nullptr, nullptr, nullptr, nullptr, "\n", " ",
|
||||
"!", "\"", "#", "¤", "%", "&", "/", "§", "½",
|
||||
"(", ")", "[", "]", "{", "}",
|
||||
"=", "?", "+", "\\", "´", "`", "¨", "¸", "\b", "@", "£", "$", "€",
|
||||
|
|
|
@ -22,15 +22,15 @@ namespace LibInput
|
|||
consteval uint8_t keycode_normal(uint8_t row, uint8_t col)
|
||||
{
|
||||
BANAN_CONSTEVAL_STATIC_ASSERT(row <= 0b111 - 1);
|
||||
BANAN_CONSTEVAL_STATIC_ASSERT(col <= 0b11111 - 8);
|
||||
BANAN_CONSTEVAL_STATIC_ASSERT(col < 0b11111 - 8);
|
||||
return ((row + 1) << 5) | col;
|
||||
}
|
||||
|
||||
consteval uint8_t keycode_numpad(uint8_t row, uint8_t col)
|
||||
{
|
||||
BANAN_CONSTEVAL_STATIC_ASSERT(row <= 0b111 - 1);
|
||||
BANAN_CONSTEVAL_STATIC_ASSERT(col < 8);
|
||||
return ((row + 1) << 5) | (col + 0b11111 - 8 + 1);
|
||||
BANAN_CONSTEVAL_STATIC_ASSERT(col <= 8);
|
||||
return ((row + 1) << 5) | (col + 0b11111 - 8);
|
||||
}
|
||||
|
||||
enum class Key
|
||||
|
|
|
@ -116,14 +116,11 @@ uint64_t AudioServer::update()
|
|||
if (!anyone_playing)
|
||||
return 60'000;
|
||||
|
||||
const uint32_t sample_frames_per_10ms = m_sample_rate / 100;
|
||||
if (max_sample_frames_to_queue < sample_frames_per_10ms)
|
||||
{
|
||||
const uint32_t sample_frames_sent = m_samples_sent / m_channels;
|
||||
if (sample_frames_sent >= sample_frames_per_10ms)
|
||||
return 1;
|
||||
max_sample_frames_to_queue = sample_frames_per_10ms;
|
||||
}
|
||||
// FIXME: this works but if any client stops producing audio samples
|
||||
// the whole audio server halts
|
||||
const uint32_t samples_per_10ms = m_sample_rate / 100;
|
||||
if (max_sample_frames_to_queue < samples_per_10ms)
|
||||
return 1;
|
||||
|
||||
for (auto& [_, buffer] : m_audio_buffers)
|
||||
{
|
||||
|
@ -138,7 +135,7 @@ uint64_t AudioServer::update()
|
|||
continue;
|
||||
|
||||
const size_t sample_frames_to_queue = BAN::Math::min<size_t>(max_sample_frames_to_queue, buffer_sample_frames_available);
|
||||
if (sample_frames_to_queue < sample_frames_per_10ms)
|
||||
if (sample_frames_to_queue < samples_per_10ms)
|
||||
continue;
|
||||
|
||||
while (m_samples.size() < queued_samples_end + sample_frames_to_queue * m_channels)
|
||||
|
|
|
@ -190,19 +190,6 @@ struct LoadedElf
|
|||
bool is_relocating;
|
||||
|
||||
char path[PATH_MAX];
|
||||
|
||||
struct LoadedPHDR
|
||||
{
|
||||
uintptr_t base;
|
||||
size_t size;
|
||||
};
|
||||
LoadedPHDR loaded_phdrs[16];
|
||||
size_t loaded_phdr_count;
|
||||
|
||||
size_t real_symtab_size;
|
||||
size_t real_symtab_entsize;
|
||||
const uint8_t* real_symtab_addr;
|
||||
const uint8_t* real_strtab_addr;
|
||||
};
|
||||
|
||||
static LoadedElf s_loaded_files[128];
|
||||
|
@ -446,7 +433,6 @@ extern "C" int __dlclose(void* handle);
|
|||
extern "C" char* __dlerror(void);
|
||||
extern "C" void* __dlopen(const char* file, int mode);
|
||||
extern "C" void* __dlsym(void* __restrict handle, const char* __restrict name);
|
||||
extern "C" int __dladdr(const void* addr, Dl_info_t* dlip);
|
||||
|
||||
template<typename RelocT> requires BAN::is_same_v<RelocT, ElfNativeRelocation> || BAN::is_same_v<RelocT, ElfNativeRelocationA>
|
||||
static uintptr_t handle_relocation(const LoadedElf& elf, const RelocT& reloc, bool resolve_symbols)
|
||||
|
@ -472,7 +458,6 @@ static uintptr_t handle_relocation(const LoadedElf& elf, const RelocT& reloc, bo
|
|||
CHECK_SYM(__dlerror);
|
||||
CHECK_SYM(__dlopen);
|
||||
CHECK_SYM(__dlsym);
|
||||
CHECK_SYM(__dladdr);
|
||||
#undef CHECK_SYM
|
||||
else if (symbol.st_shndx && ELF_ST_BIND(symbol.st_info) != STB_WEAK)
|
||||
symbol_address = elf.base + symbol.st_value;
|
||||
|
@ -962,64 +947,6 @@ static void load_program_header(const ElfNativeProgramHeader& program_header, in
|
|||
}
|
||||
}
|
||||
|
||||
static bool read_section_header(const LoadedElf& elf, size_t index, ElfNativeSectionHeader& header)
|
||||
{
|
||||
if (index >= elf.file_header.e_shnum)
|
||||
return false;
|
||||
|
||||
const auto& file_header = elf.file_header;
|
||||
if (syscall(SYS_PREAD, elf.fd, &header, sizeof(header), file_header.e_shoff + index * file_header.e_shentsize) != sizeof(header))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static const uint8_t* mmap_section_header_data(const LoadedElf& elf, const ElfNativeSectionHeader& header)
|
||||
{
|
||||
const size_t offset_in_page = header.sh_offset % PAGE_SIZE;
|
||||
const sys_mmap_t mmap_args {
|
||||
.addr = nullptr,
|
||||
.len = header.sh_size + offset_in_page,
|
||||
.prot = PROT_READ,
|
||||
.flags = MAP_SHARED,
|
||||
.fildes = elf.fd,
|
||||
.off = static_cast<off_t>(header.sh_offset - offset_in_page),
|
||||
};
|
||||
|
||||
const uint8_t* mmap_ret = reinterpret_cast<const uint8_t*>(syscall(SYS_MMAP, &mmap_args));
|
||||
if (mmap_ret == MAP_FAILED)
|
||||
return nullptr;
|
||||
|
||||
return mmap_ret + offset_in_page;
|
||||
}
|
||||
|
||||
static bool load_symbol_table(LoadedElf& elf)
|
||||
{
|
||||
if (elf.file_header.e_shentsize < sizeof(ElfNativeSectionHeader))
|
||||
return false;
|
||||
|
||||
for (size_t i = 0; i < elf.file_header.e_shnum; i++)
|
||||
{
|
||||
ElfNativeSectionHeader symtab_header;
|
||||
if (!read_section_header(elf, i, symtab_header))
|
||||
return false;
|
||||
if (symtab_header.sh_type != SHT_SYMTAB)
|
||||
continue;
|
||||
|
||||
ElfNativeSectionHeader strtab_header;
|
||||
if (!read_section_header(elf, symtab_header.sh_link, strtab_header))
|
||||
return false;
|
||||
|
||||
elf.real_symtab_entsize = symtab_header.sh_entsize;
|
||||
elf.real_symtab_size = symtab_header.sh_size;
|
||||
elf.real_symtab_addr = mmap_section_header_data(elf, symtab_header);
|
||||
elf.real_strtab_addr = mmap_section_header_data(elf, strtab_header);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
static LoadedElf& load_elf(const char* path, int fd)
|
||||
{
|
||||
for (size_t i = 0; i < s_loaded_file_count; i++)
|
||||
|
@ -1094,13 +1021,8 @@ static LoadedElf& load_elf(const char* path, int fd)
|
|||
break;
|
||||
}
|
||||
|
||||
auto& elf = s_loaded_files[s_loaded_file_count++];
|
||||
elf.tls_header.p_type = PT_NULL;
|
||||
elf.base = base;
|
||||
elf.fd = fd;
|
||||
elf.dynamics = nullptr;
|
||||
memcpy(&elf.file_header, &file_header, sizeof(file_header));
|
||||
strcpy(elf.path, path);
|
||||
ElfNativeProgramHeader tls_header {};
|
||||
tls_header.p_type = PT_NULL;
|
||||
|
||||
for (size_t i = 0; i < file_header.e_phnum; i++)
|
||||
{
|
||||
|
@ -1121,20 +1043,10 @@ static LoadedElf& load_elf(const char* path, int fd)
|
|||
case PT_GNU_RELRO:
|
||||
break;
|
||||
case PT_TLS:
|
||||
elf.tls_header = program_header;
|
||||
tls_header = program_header;
|
||||
break;
|
||||
case PT_LOAD:
|
||||
if (elf.loaded_phdr_count >= sizeof(elf.loaded_phdrs) / sizeof(*elf.loaded_phdrs))
|
||||
{
|
||||
print(STDERR_FILENO, "file '");
|
||||
print(STDERR_FILENO, elf.path);
|
||||
print_error_and_exit("' has too many PT_LOAD headers", 0);
|
||||
}
|
||||
program_header.p_vaddr += base;
|
||||
elf.loaded_phdrs[elf.loaded_phdr_count++] = {
|
||||
.base = program_header.p_vaddr,
|
||||
.size = program_header.p_memsz,
|
||||
};
|
||||
load_program_header(program_header, fd, needs_writable);
|
||||
break;
|
||||
default:
|
||||
|
@ -1144,6 +1056,13 @@ static LoadedElf& load_elf(const char* path, int fd)
|
|||
}
|
||||
}
|
||||
|
||||
auto& elf = s_loaded_files[s_loaded_file_count++];
|
||||
elf.tls_header = tls_header;
|
||||
elf.base = base;
|
||||
elf.fd = fd;
|
||||
elf.dynamics = nullptr;
|
||||
memcpy(&elf.file_header, &file_header, sizeof(file_header));
|
||||
strcpy(elf.path, path);
|
||||
|
||||
if (has_dynamic_pheader)
|
||||
{
|
||||
|
@ -1165,8 +1084,6 @@ static LoadedElf& load_elf(const char* path, int fd)
|
|||
handle_dynamic(elf);
|
||||
}
|
||||
|
||||
load_symbol_table(elf);
|
||||
|
||||
return elf;
|
||||
}
|
||||
|
||||
|
@ -1502,88 +1419,6 @@ void* __dlsym(void* __restrict handle, const char* __restrict name)
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
static bool elf_contains_address(const LoadedElf& elf, const void* address)
|
||||
{
|
||||
const uintptr_t addr_uptr = reinterpret_cast<uintptr_t>(address);
|
||||
for (size_t i = 0; i < elf.loaded_phdr_count; i++)
|
||||
{
|
||||
const auto& phdr = elf.loaded_phdrs[i];
|
||||
if (phdr.base <= addr_uptr && addr_uptr < phdr.base + phdr.size)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
struct FindSymbolResult
|
||||
{
|
||||
const char* name;
|
||||
void* addr;
|
||||
};
|
||||
|
||||
static FindSymbolResult find_symbol_containing(const LoadedElf& elf, const void* address)
|
||||
{
|
||||
const uintptr_t addr_uptr = reinterpret_cast<uintptr_t>(address);
|
||||
|
||||
const size_t symbol_count = reinterpret_cast<const uint32_t*>(elf.hash)[1];
|
||||
for (size_t i = 1; i < symbol_count; i++)
|
||||
{
|
||||
const auto& symbol = *reinterpret_cast<const ElfNativeSymbol*>(elf.symtab + i * elf.syment);
|
||||
const uintptr_t symbol_base = elf.base + symbol.st_value;
|
||||
if (!(symbol_base <= addr_uptr && addr_uptr < symbol_base + symbol.st_size))
|
||||
continue;
|
||||
return {
|
||||
.name = reinterpret_cast<const char*>(elf.strtab + symbol.st_name),
|
||||
.addr = reinterpret_cast<void*>(symbol_base),
|
||||
};
|
||||
}
|
||||
|
||||
if (!elf.real_symtab_addr || !elf.real_strtab_addr)
|
||||
return {};
|
||||
|
||||
for (size_t i = 1; i < elf.real_symtab_size / elf.real_symtab_entsize; i++)
|
||||
{
|
||||
const auto& symbol = *reinterpret_cast<const ElfNativeSymbol*>(elf.real_symtab_addr + i * elf.real_symtab_entsize);
|
||||
const uintptr_t symbol_base = elf.base + symbol.st_value;
|
||||
if (!(symbol_base <= addr_uptr && addr_uptr < symbol_base + symbol.st_size))
|
||||
continue;
|
||||
return {
|
||||
.name = reinterpret_cast<const char*>(elf.real_strtab_addr + symbol.st_name),
|
||||
.addr = reinterpret_cast<void*>(symbol_base),
|
||||
};
|
||||
}
|
||||
|
||||
return {};
|
||||
}
|
||||
|
||||
int __dladdr(const void* addr, Dl_info_t* dlip)
|
||||
{
|
||||
for (size_t i = 0; i < s_loaded_file_count; i++)
|
||||
{
|
||||
const auto& elf = s_loaded_files[i];
|
||||
if (!elf_contains_address(elf, addr))
|
||||
continue;
|
||||
|
||||
dlip->dli_fname = elf.path;
|
||||
dlip->dli_fbase = reinterpret_cast<void*>(elf.base);
|
||||
|
||||
if (const auto symbol = find_symbol_containing(elf, addr); symbol.addr && symbol.name)
|
||||
{
|
||||
dlip->dli_sname = symbol.name;
|
||||
dlip->dli_saddr = symbol.addr;
|
||||
}
|
||||
else
|
||||
{
|
||||
dlip->dli_sname = nullptr;
|
||||
dlip->dli_saddr = nullptr;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
s_dlerror_string = "address is not contained in any file";
|
||||
return 0;
|
||||
}
|
||||
|
||||
static LibELF::AuxiliaryVector* find_auxv(char** envp)
|
||||
{
|
||||
if (envp == nullptr)
|
||||
|
|
|
@ -181,6 +181,13 @@ void Terminal::run()
|
|||
perror("ioctl");
|
||||
return;
|
||||
}
|
||||
|
||||
const pid_t fgpgrp = tcgetpgrp(m_shell_info.pts_master);
|
||||
if (fgpgrp == -1)
|
||||
{
|
||||
perror("tcgetpgrp");
|
||||
return;
|
||||
}
|
||||
});
|
||||
|
||||
const int max_fd = BAN::Math::max(m_shell_info.pts_master, m_window->server_fd());
|
||||
|
@ -669,14 +676,6 @@ Rectangle Terminal::putcodepoint(uint32_t codepoint)
|
|||
auto& texture = m_window->texture();
|
||||
switch (codepoint)
|
||||
{
|
||||
case 0x00: // null
|
||||
case 0x01: // start of heading
|
||||
case 0x02: // start of text
|
||||
case 0x1C: // file separator
|
||||
case 0x1D: // group separator
|
||||
case 0x1E: // record separator
|
||||
case 0x1F: // unit separator
|
||||
break;
|
||||
case '\a':
|
||||
// TODO: bell
|
||||
break;
|
||||
|
|
|
@ -90,7 +90,7 @@ void WindowServer::on_window_create(int fd, const LibGUI::WindowPacket::WindowCr
|
|||
|
||||
window_popper.disable();
|
||||
|
||||
if (packet.attributes.shown && packet.attributes.focusable)
|
||||
if (packet.attributes.focusable)
|
||||
set_focused_window(window);
|
||||
else if (m_client_windows.size() > 1)
|
||||
BAN::swap(m_client_windows[m_client_windows.size() - 1], m_client_windows[m_client_windows.size() - 2]);
|
||||
|
@ -197,9 +197,6 @@ void WindowServer::on_window_set_attributes(int fd, const LibGUI::WindowPacket::
|
|||
};
|
||||
if (auto ret = event_packet.send_serialized(target_window->client_fd()); ret.is_error())
|
||||
dwarnln("could not send window shown event: {}", ret.error());
|
||||
|
||||
if (packet.attributes.focusable && packet.attributes.shown)
|
||||
set_focused_window(target_window);
|
||||
}
|
||||
|
||||
void WindowServer::on_window_set_mouse_relative(int fd, const LibGUI::WindowPacket::WindowSetMouseRelative& packet)
|
||||
|
@ -515,9 +512,7 @@ void WindowServer::on_mouse_button(LibInput::MouseButtonEvent event)
|
|||
}
|
||||
|
||||
BAN::RefPtr<Window> target_window;
|
||||
if (m_state == State::Fullscreen)
|
||||
target_window = m_focused_window;
|
||||
if (!event.pressed && !target_window)
|
||||
if (!event.pressed)
|
||||
target_window = m_mouse_button_windows[button_idx];
|
||||
for (size_t i = m_client_windows.size(); i > 0 && !target_window; i--)
|
||||
if (m_client_windows[i - 1]->full_area().contains(m_cursor) && m_client_windows[i - 1]->get_attributes().shown)
|
||||
|
@ -561,7 +556,7 @@ void WindowServer::on_mouse_button(LibInput::MouseButtonEvent event)
|
|||
if (event.button == LibInput::MouseButton::Left && !event.pressed && target_window->close_button_area().contains(m_cursor))
|
||||
{
|
||||
LibGUI::EventPacket::CloseWindowEvent packet;
|
||||
if (auto ret = packet.send_serialized(target_window->client_fd()); ret.is_error())
|
||||
if (auto ret = packet.send_serialized(m_focused_window->client_fd()); ret.is_error())
|
||||
dwarnln("could not send close window event: {}", ret.error());
|
||||
break;
|
||||
}
|
||||
|
@ -573,9 +568,9 @@ void WindowServer::on_mouse_button(LibInput::MouseButtonEvent event)
|
|||
LibGUI::EventPacket::MouseButtonEvent packet;
|
||||
packet.event.button = event.button;
|
||||
packet.event.pressed = event.pressed;
|
||||
packet.event.x = m_cursor.x - target_window->client_x();
|
||||
packet.event.y = m_cursor.y - target_window->client_y();
|
||||
if (auto ret = packet.send_serialized(target_window->client_fd()); ret.is_error())
|
||||
packet.event.x = m_cursor.x - m_focused_window->client_x();
|
||||
packet.event.y = m_cursor.y - m_focused_window->client_y();
|
||||
if (auto ret = packet.send_serialized(m_focused_window->client_fd()); ret.is_error())
|
||||
{
|
||||
dwarnln("could not send mouse button event: {}", ret.error());
|
||||
return;
|
||||
|
@ -784,17 +779,6 @@ void WindowServer::set_focused_window(BAN::RefPtr<Window> window)
|
|||
invalidate(cursor_area());
|
||||
}
|
||||
|
||||
if (m_focused_window)
|
||||
{
|
||||
LibGUI::EventPacket::WindowFocusEvent packet;
|
||||
packet.event.focused = false;
|
||||
if (auto ret = packet.send_serialized(m_focused_window->client_fd()); ret.is_error())
|
||||
{
|
||||
dwarnln("could not send window focus event: {}", ret.error());
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
for (size_t i = m_client_windows.size(); i > 0; i--)
|
||||
{
|
||||
if (m_client_windows[i - 1] == window)
|
||||
|
@ -806,17 +790,6 @@ void WindowServer::set_focused_window(BAN::RefPtr<Window> window)
|
|||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (m_focused_window)
|
||||
{
|
||||
LibGUI::EventPacket::WindowFocusEvent packet;
|
||||
packet.event.focused = true;
|
||||
if (auto ret = packet.send_serialized(m_focused_window->client_fd()); ret.is_error())
|
||||
{
|
||||
dwarnln("could not send window focus event: {}", ret.error());
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static uint32_t alpha_blend(uint32_t color_a, uint32_t color_b)
|
||||
|
@ -1437,10 +1410,6 @@ void WindowServer::remove_client_fd(int fd)
|
|||
invalidate(m_framebuffer.area());
|
||||
}
|
||||
|
||||
for (auto& window : m_mouse_button_windows)
|
||||
if (window && window->client_fd() == fd)
|
||||
window.clear();
|
||||
|
||||
for (size_t i = 0; i < m_client_windows.size(); i++)
|
||||
{
|
||||
auto window = m_client_windows[i];
|
||||
|
|
Loading…
Reference in New Issue