Merge branch 'master' into d3d12
This commit is contained in:
@@ -19,13 +19,13 @@
|
||||
#include "xenia/base/string.h"
|
||||
#include "xenia/cpu/processor.h"
|
||||
#include "xenia/emulator.h"
|
||||
#include "xenia/kernel/notify_listener.h"
|
||||
#include "xenia/kernel/user_module.h"
|
||||
#include "xenia/kernel/util/shim_utils.h"
|
||||
#include "xenia/kernel/xam/xam_module.h"
|
||||
#include "xenia/kernel/xboxkrnl/xboxkrnl_module.h"
|
||||
#include "xenia/kernel/xevent.h"
|
||||
#include "xenia/kernel/xmodule.h"
|
||||
#include "xenia/kernel/xnotifylistener.h"
|
||||
#include "xenia/kernel/xobject.h"
|
||||
#include "xenia/kernel/xthread.h"
|
||||
|
||||
@@ -573,7 +573,7 @@ object_ref<XThread> KernelState::GetThreadByID(uint32_t thread_id) {
|
||||
return retain_object(thread);
|
||||
}
|
||||
|
||||
void KernelState::RegisterNotifyListener(NotifyListener* listener) {
|
||||
void KernelState::RegisterNotifyListener(XNotifyListener* listener) {
|
||||
auto global_lock = global_critical_region_.Acquire();
|
||||
notify_listeners_.push_back(retain_object(listener));
|
||||
|
||||
@@ -597,7 +597,7 @@ void KernelState::RegisterNotifyListener(NotifyListener* listener) {
|
||||
}
|
||||
}
|
||||
|
||||
void KernelState::UnregisterNotifyListener(NotifyListener* listener) {
|
||||
void KernelState::UnregisterNotifyListener(XNotifyListener* listener) {
|
||||
auto global_lock = global_critical_region_.Acquire();
|
||||
for (auto it = notify_listeners_.begin(); it != notify_listeners_.end();
|
||||
++it) {
|
||||
|
||||
@@ -48,7 +48,7 @@ class Dispatcher;
|
||||
class XHostThread;
|
||||
class KernelModule;
|
||||
class XModule;
|
||||
class NotifyListener;
|
||||
class XNotifyListener;
|
||||
class XThread;
|
||||
class UserModule;
|
||||
|
||||
@@ -158,8 +158,8 @@ class KernelState {
|
||||
void OnThreadExit(XThread* thread);
|
||||
object_ref<XThread> GetThreadByID(uint32_t thread_id);
|
||||
|
||||
void RegisterNotifyListener(NotifyListener* listener);
|
||||
void UnregisterNotifyListener(NotifyListener* listener);
|
||||
void RegisterNotifyListener(XNotifyListener* listener);
|
||||
void UnregisterNotifyListener(XNotifyListener* listener);
|
||||
void BroadcastNotification(XNotificationID id, uint32_t data);
|
||||
|
||||
util::NativeList* dpc_list() { return &dpc_list_; }
|
||||
@@ -196,7 +196,7 @@ class KernelState {
|
||||
// Must be guarded by the global critical region.
|
||||
util::ObjectTable object_table_;
|
||||
std::unordered_map<uint32_t, XThread*> threads_by_id_;
|
||||
std::vector<object_ref<NotifyListener>> notify_listeners_;
|
||||
std::vector<object_ref<XNotifyListener>> notify_listeners_;
|
||||
bool has_notified_startup_ = false;
|
||||
|
||||
uint32_t process_type_ = X_PROCTYPE_USER;
|
||||
|
||||
@@ -9,9 +9,9 @@
|
||||
|
||||
#include "xenia/base/logging.h"
|
||||
#include "xenia/kernel/kernel_state.h"
|
||||
#include "xenia/kernel/notify_listener.h"
|
||||
#include "xenia/kernel/util/shim_utils.h"
|
||||
#include "xenia/kernel/xam/xam_private.h"
|
||||
#include "xenia/kernel/xnotifylistener.h"
|
||||
#include "xenia/xbox.h"
|
||||
|
||||
namespace xe {
|
||||
@@ -23,7 +23,7 @@ dword_result_t XamNotifyCreateListenerInternal(qword_t mask, dword_t unk,
|
||||
// r4=1 may indicate user process?
|
||||
|
||||
auto listener =
|
||||
object_ref<NotifyListener>(new NotifyListener(kernel_state()));
|
||||
object_ref<XNotifyListener>(new XNotifyListener(kernel_state()));
|
||||
listener->Initialize(mask);
|
||||
|
||||
// Handle ref is incremented, so return that.
|
||||
@@ -48,7 +48,7 @@ dword_result_t XNotifyGetNext(dword_t handle, dword_t match_id,
|
||||
|
||||
// Grab listener.
|
||||
auto listener =
|
||||
kernel_state()->object_table()->LookupObject<NotifyListener>(handle);
|
||||
kernel_state()->object_table()->LookupObject<XNotifyListener>(handle);
|
||||
if (!listener) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
#include "xenia/kernel/xevent.h"
|
||||
#include "xenia/kernel/xfile.h"
|
||||
#include "xenia/kernel/xiocompletion.h"
|
||||
#include "xenia/kernel/xsymboliclink.h"
|
||||
#include "xenia/kernel/xthread.h"
|
||||
#include "xenia/vfs/device.h"
|
||||
#include "xenia/xbox.h"
|
||||
@@ -717,6 +718,64 @@ dword_result_t NtFlushBuffersFile(
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(NtFlushBuffersFile, kFileSystem, kStub);
|
||||
|
||||
// https://docs.microsoft.com/en-us/windows/win32/devnotes/ntopensymboliclinkobject
|
||||
dword_result_t NtOpenSymbolicLinkObject(
|
||||
lpdword_t handle_out, pointer_t<X_OBJECT_ATTRIBUTES> object_attrs) {
|
||||
if (!object_attrs) {
|
||||
return X_STATUS_INVALID_PARAMETER;
|
||||
}
|
||||
assert_not_null(handle_out);
|
||||
|
||||
assert_true(object_attrs->attributes == 64); // case insensitive
|
||||
|
||||
auto object_name =
|
||||
kernel_memory()->TranslateVirtual<X_ANSI_STRING*>(object_attrs->name_ptr);
|
||||
|
||||
std::string target_path =
|
||||
object_name->to_string(kernel_memory()->virtual_membase());
|
||||
if (object_attrs->root_directory != 0) {
|
||||
assert_always();
|
||||
}
|
||||
|
||||
auto pos = target_path.find("\\??\\");
|
||||
if (pos != target_path.npos && pos == 0) {
|
||||
target_path = target_path.substr(4); // Strip the full qualifier
|
||||
}
|
||||
|
||||
std::string link_path;
|
||||
if (!kernel_state()->file_system()->FindSymbolicLink(target_path,
|
||||
link_path)) {
|
||||
return X_STATUS_NO_SUCH_FILE;
|
||||
}
|
||||
|
||||
object_ref<XSymbolicLink> symlink(new XSymbolicLink(kernel_state()));
|
||||
symlink->Initialize(target_path, link_path);
|
||||
|
||||
*handle_out = symlink->handle();
|
||||
|
||||
return X_STATUS_SUCCESS;
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(NtOpenSymbolicLinkObject, kFileSystem, kImplemented);
|
||||
|
||||
// https://docs.microsoft.com/en-us/windows/win32/devnotes/ntquerysymboliclinkobject
|
||||
dword_result_t NtQuerySymbolicLinkObject(dword_t handle,
|
||||
pointer_t<X_ANSI_STRING> target) {
|
||||
auto symlink =
|
||||
kernel_state()->object_table()->LookupObject<XSymbolicLink>(handle);
|
||||
if (!symlink) {
|
||||
return X_STATUS_NO_SUCH_FILE;
|
||||
}
|
||||
auto length = std::min(static_cast<size_t>(target->maximum_length),
|
||||
symlink->target().size());
|
||||
if (length > 0) {
|
||||
auto target_buf = kernel_memory()->TranslateVirtual(target->pointer);
|
||||
std::memcpy(target_buf, symlink->target().c_str(), length);
|
||||
}
|
||||
target->length = static_cast<uint16_t>(length);
|
||||
return X_STATUS_SUCCESS;
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(NtQuerySymbolicLinkObject, kFileSystem, kImplemented);
|
||||
|
||||
dword_result_t FscGetCacheElementCount(dword_t r3) { return 0; }
|
||||
DECLARE_XBOXKRNL_EXPORT1(FscGetCacheElementCount, kFileSystem, kStub);
|
||||
|
||||
|
||||
@@ -543,6 +543,12 @@ dword_result_t ExAllocatePoolTypeWithTag(dword_t size, dword_t tag,
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(ExAllocatePoolTypeWithTag, kMemory, kImplemented);
|
||||
|
||||
dword_result_t ExAllocatePool(dword_t size) {
|
||||
const uint32_t none = 0x656E6F4E; // 'None'
|
||||
return ExAllocatePoolTypeWithTag(size, none, 0);
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(ExAllocatePool, kMemory, kImplemented);
|
||||
|
||||
void ExFreePool(lpvoid_t base_address) {
|
||||
kernel_state()->memory()->SystemHeapFree(base_address);
|
||||
}
|
||||
|
||||
@@ -312,6 +312,30 @@ dword_result_t RtlUnicodeToMultiByteN(pointer_t<uint8_t> destination_ptr,
|
||||
DECLARE_XBOXKRNL_EXPORT3(RtlUnicodeToMultiByteN, kNone, kImplemented,
|
||||
kHighFrequency, kSketchy);
|
||||
|
||||
// https://undocumented.ntinternals.net/UserMode/Undocumented%20Functions/Executable%20Images/RtlImageNtHeader.html
|
||||
pointer_result_t RtlImageNtHeader(lpvoid_t module) {
|
||||
if (!module) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Little-endian! no swapping!
|
||||
|
||||
auto dos_header = module.as<const uint8_t*>();
|
||||
auto dos_magic = *reinterpret_cast<const uint16_t*>(&dos_header[0x00]);
|
||||
if (dos_magic != 0x5A4D) { // 'MZ'
|
||||
return 0;
|
||||
}
|
||||
auto dos_lfanew = *reinterpret_cast<const int32_t*>(&dos_header[0x3C]);
|
||||
|
||||
auto nt_header = &dos_header[dos_lfanew];
|
||||
auto nt_magic = *reinterpret_cast<const uint32_t*>(&nt_header[0x00]);
|
||||
if (nt_magic != 0x4550) { // 'PE'
|
||||
return 0;
|
||||
}
|
||||
return static_cast<uint32_t>(nt_header - kernel_memory()->virtual_membase());
|
||||
}
|
||||
DECLARE_XBOXKRNL_EXPORT1(RtlImageNtHeader, kNone, kImplemented);
|
||||
|
||||
pointer_result_t RtlImageXexHeaderField(pointer_t<xex2_header> xex_header,
|
||||
dword_t field_dword) {
|
||||
uint32_t field_value = 0;
|
||||
|
||||
@@ -14,7 +14,7 @@ namespace kernel {
|
||||
|
||||
XEnumerator::XEnumerator(KernelState* kernel_state, size_t items_per_enumerate,
|
||||
size_t item_size)
|
||||
: XObject(kernel_state, kTypeEnumerator),
|
||||
: XObject(kernel_state, kType),
|
||||
items_per_enumerate_(items_per_enumerate),
|
||||
item_size_(item_size) {}
|
||||
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XEvent::XEvent(KernelState* kernel_state) : XObject(kernel_state, kTypeEvent) {}
|
||||
XEvent::XEvent(KernelState* kernel_state) : XObject(kernel_state, kType) {}
|
||||
|
||||
XEvent::~XEvent() = default;
|
||||
|
||||
|
||||
@@ -20,13 +20,11 @@ namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XFile::XFile(KernelState* kernel_state, vfs::File* file, bool synchronous)
|
||||
: XObject(kernel_state, kTypeFile),
|
||||
file_(file),
|
||||
is_synchronous_(synchronous) {
|
||||
: XObject(kernel_state, kType), file_(file), is_synchronous_(synchronous) {
|
||||
async_event_ = threading::Event::CreateAutoResetEvent(false);
|
||||
}
|
||||
|
||||
XFile::XFile() : XObject(kTypeFile) {
|
||||
XFile::XFile() : XObject(kType) {
|
||||
async_event_ = threading::Event::CreateAutoResetEvent(false);
|
||||
}
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@ namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XIOCompletion::XIOCompletion(KernelState* kernel_state)
|
||||
: XObject(kernel_state, kTypeIOCompletion) {
|
||||
: XObject(kernel_state, kType) {
|
||||
notification_semaphore_ = threading::Semaphore::Create(0, kMaxNotifications);
|
||||
}
|
||||
|
||||
|
||||
@@ -19,7 +19,7 @@ namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XModule::XModule(KernelState* kernel_state, ModuleType module_type)
|
||||
: XObject(kernel_state, kTypeModule),
|
||||
: XObject(kernel_state, kType),
|
||||
module_type_(module_type),
|
||||
processor_module_(nullptr),
|
||||
hmodule_ptr_(0) {
|
||||
|
||||
@@ -17,10 +17,9 @@
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XMutant::XMutant() : XObject(kTypeMutant) {}
|
||||
XMutant::XMutant() : XObject(kType) {}
|
||||
|
||||
XMutant::XMutant(KernelState* kernel_state)
|
||||
: XObject(kernel_state, kTypeMutant) {}
|
||||
XMutant::XMutant(KernelState* kernel_state) : XObject(kernel_state, kType) {}
|
||||
|
||||
XMutant::~XMutant() = default;
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
******************************************************************************
|
||||
*/
|
||||
|
||||
#include "xenia/kernel/notify_listener.h"
|
||||
#include "xenia/kernel/xnotifylistener.h"
|
||||
|
||||
#include "xenia/base/byte_stream.h"
|
||||
#include "xenia/kernel/kernel_state.h"
|
||||
@@ -15,12 +15,12 @@
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
NotifyListener::NotifyListener(KernelState* kernel_state)
|
||||
: XObject(kernel_state, kTypeNotifyListener) {}
|
||||
XNotifyListener::XNotifyListener(KernelState* kernel_state)
|
||||
: XObject(kernel_state, kType) {}
|
||||
|
||||
NotifyListener::~NotifyListener() {}
|
||||
XNotifyListener::~XNotifyListener() {}
|
||||
|
||||
void NotifyListener::Initialize(uint64_t mask) {
|
||||
void XNotifyListener::Initialize(uint64_t mask) {
|
||||
assert_false(wait_handle_);
|
||||
|
||||
wait_handle_ = xe::threading::Event::CreateManualResetEvent(false);
|
||||
@@ -29,7 +29,7 @@ void NotifyListener::Initialize(uint64_t mask) {
|
||||
kernel_state_->RegisterNotifyListener(this);
|
||||
}
|
||||
|
||||
void NotifyListener::EnqueueNotification(XNotificationID id, uint32_t data) {
|
||||
void XNotifyListener::EnqueueNotification(XNotificationID id, uint32_t data) {
|
||||
// Ignore if the notification doesn't match our mask.
|
||||
if ((mask_ & uint64_t(1ULL << (id >> 25))) == 0) {
|
||||
return;
|
||||
@@ -47,8 +47,8 @@ void NotifyListener::EnqueueNotification(XNotificationID id, uint32_t data) {
|
||||
wait_handle_->Set();
|
||||
}
|
||||
|
||||
bool NotifyListener::DequeueNotification(XNotificationID* out_id,
|
||||
uint32_t* out_data) {
|
||||
bool XNotifyListener::DequeueNotification(XNotificationID* out_id,
|
||||
uint32_t* out_data) {
|
||||
auto global_lock = global_critical_region_.Acquire();
|
||||
bool dequeued = false;
|
||||
if (notification_count_) {
|
||||
@@ -65,8 +65,8 @@ bool NotifyListener::DequeueNotification(XNotificationID* out_id,
|
||||
return dequeued;
|
||||
}
|
||||
|
||||
bool NotifyListener::DequeueNotification(XNotificationID id,
|
||||
uint32_t* out_data) {
|
||||
bool XNotifyListener::DequeueNotification(XNotificationID id,
|
||||
uint32_t* out_data) {
|
||||
auto global_lock = global_critical_region_.Acquire();
|
||||
bool dequeued = false;
|
||||
if (notification_count_) {
|
||||
@@ -84,7 +84,7 @@ bool NotifyListener::DequeueNotification(XNotificationID id,
|
||||
return dequeued;
|
||||
}
|
||||
|
||||
bool NotifyListener::Save(ByteStream* stream) {
|
||||
bool XNotifyListener::Save(ByteStream* stream) {
|
||||
SaveObject(stream);
|
||||
|
||||
stream->Write(mask_);
|
||||
@@ -99,9 +99,9 @@ bool NotifyListener::Save(ByteStream* stream) {
|
||||
return true;
|
||||
}
|
||||
|
||||
object_ref<NotifyListener> NotifyListener::Restore(KernelState* kernel_state,
|
||||
ByteStream* stream) {
|
||||
auto notify = new NotifyListener(nullptr);
|
||||
object_ref<XNotifyListener> XNotifyListener::Restore(KernelState* kernel_state,
|
||||
ByteStream* stream) {
|
||||
auto notify = new XNotifyListener(nullptr);
|
||||
notify->kernel_state_ = kernel_state;
|
||||
|
||||
notify->RestoreObject(stream);
|
||||
@@ -115,7 +115,7 @@ object_ref<NotifyListener> NotifyListener::Restore(KernelState* kernel_state,
|
||||
notify->notifications_.insert(pair);
|
||||
}
|
||||
|
||||
return object_ref<NotifyListener>(notify);
|
||||
return object_ref<XNotifyListener>(notify);
|
||||
}
|
||||
|
||||
} // namespace kernel
|
||||
@@ -7,8 +7,8 @@
|
||||
******************************************************************************
|
||||
*/
|
||||
|
||||
#ifndef XENIA_KERNEL_NOTIFY_LISTENER_H_
|
||||
#define XENIA_KERNEL_NOTIFY_LISTENER_H_
|
||||
#ifndef XENIA_KERNEL_XNOTIFYLISTENER_H_
|
||||
#define XENIA_KERNEL_XNOTIFYLISTENER_H_
|
||||
|
||||
#include <memory>
|
||||
#include <unordered_map>
|
||||
@@ -21,12 +21,12 @@
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
class NotifyListener : public XObject {
|
||||
class XNotifyListener : public XObject {
|
||||
public:
|
||||
static const Type kType = kTypeNotifyListener;
|
||||
|
||||
explicit NotifyListener(KernelState* kernel_state);
|
||||
~NotifyListener() override;
|
||||
explicit XNotifyListener(KernelState* kernel_state);
|
||||
~XNotifyListener() override;
|
||||
|
||||
uint64_t mask() const { return mask_; }
|
||||
|
||||
@@ -37,8 +37,8 @@ class NotifyListener : public XObject {
|
||||
bool DequeueNotification(XNotificationID id, uint32_t* out_data);
|
||||
|
||||
bool Save(ByteStream* stream) override;
|
||||
static object_ref<NotifyListener> Restore(KernelState* kernel_state,
|
||||
ByteStream* stream);
|
||||
static object_ref<XNotifyListener> Restore(KernelState* kernel_state,
|
||||
ByteStream* stream);
|
||||
|
||||
protected:
|
||||
xe::threading::WaitHandle* GetWaitHandle() override {
|
||||
@@ -56,4 +56,4 @@ class NotifyListener : public XObject {
|
||||
} // namespace kernel
|
||||
} // namespace xe
|
||||
|
||||
#endif // XENIA_KERNEL_NOTIFY_LISTENER_H_
|
||||
#endif // XENIA_KERNEL_XNOTIFYLISTENER_H_
|
||||
@@ -14,14 +14,15 @@
|
||||
#include "xenia/base/byte_stream.h"
|
||||
#include "xenia/base/clock.h"
|
||||
#include "xenia/kernel/kernel_state.h"
|
||||
#include "xenia/kernel/notify_listener.h"
|
||||
#include "xenia/kernel/xboxkrnl/xboxkrnl_private.h"
|
||||
#include "xenia/kernel/xenumerator.h"
|
||||
#include "xenia/kernel/xevent.h"
|
||||
#include "xenia/kernel/xfile.h"
|
||||
#include "xenia/kernel/xmodule.h"
|
||||
#include "xenia/kernel/xmutant.h"
|
||||
#include "xenia/kernel/xnotifylistener.h"
|
||||
#include "xenia/kernel/xsemaphore.h"
|
||||
#include "xenia/kernel/xsymboliclink.h"
|
||||
#include "xenia/kernel/xthread.h"
|
||||
|
||||
namespace xe {
|
||||
@@ -139,13 +140,15 @@ object_ref<XObject> XObject::Restore(KernelState* kernel_state, Type type,
|
||||
case kTypeMutant:
|
||||
return XMutant::Restore(kernel_state, stream);
|
||||
case kTypeNotifyListener:
|
||||
return NotifyListener::Restore(kernel_state, stream);
|
||||
return XNotifyListener::Restore(kernel_state, stream);
|
||||
case kTypeSemaphore:
|
||||
return XSemaphore::Restore(kernel_state, stream);
|
||||
case kTypeSession:
|
||||
break;
|
||||
case kTypeSocket:
|
||||
break;
|
||||
case kTypeSymbolicLink:
|
||||
return XSymbolicLink::Restore(kernel_state, stream);
|
||||
case kTypeThread:
|
||||
return XThread::Restore(kernel_state, stream);
|
||||
case kTypeTimer:
|
||||
|
||||
@@ -121,6 +121,7 @@ class XObject {
|
||||
kTypeSemaphore,
|
||||
kTypeSession,
|
||||
kTypeSocket,
|
||||
kTypeSymbolicLink,
|
||||
kTypeThread,
|
||||
kTypeTimer,
|
||||
};
|
||||
|
||||
@@ -31,12 +31,10 @@
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XSocket::XSocket(KernelState* kernel_state)
|
||||
: XObject(kernel_state, XObject::kTypeSocket) {}
|
||||
XSocket::XSocket(KernelState* kernel_state) : XObject(kernel_state, kType) {}
|
||||
|
||||
XSocket::XSocket(KernelState* kernel_state, uint64_t native_handle)
|
||||
: XObject(kernel_state, XObject::kTypeSocket),
|
||||
native_handle_(native_handle) {}
|
||||
: XObject(kernel_state, kType), native_handle_(native_handle) {}
|
||||
|
||||
XSocket::~XSocket() { Close(); }
|
||||
|
||||
|
||||
58
src/xenia/kernel/xsymboliclink.cc
Normal file
58
src/xenia/kernel/xsymboliclink.cc
Normal file
@@ -0,0 +1,58 @@
|
||||
/**
|
||||
******************************************************************************
|
||||
* Xenia : Xbox 360 Emulator Research Project *
|
||||
******************************************************************************
|
||||
* Copyright 2013 Ben Vanik. All rights reserved. *
|
||||
* Released under the BSD license - see LICENSE in the root for more details. *
|
||||
******************************************************************************
|
||||
*/
|
||||
|
||||
#include "xenia/kernel/xsymboliclink.h"
|
||||
|
||||
#include "xenia/base/byte_stream.h"
|
||||
#include "xenia/kernel/kernel_state.h"
|
||||
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XSymbolicLink::XSymbolicLink(KernelState* kernel_state)
|
||||
: XObject(kernel_state, kType), path_(), target_() {}
|
||||
|
||||
XSymbolicLink::XSymbolicLink() : XObject(kType), path_(), target_() {}
|
||||
|
||||
XSymbolicLink::~XSymbolicLink() {}
|
||||
|
||||
void XSymbolicLink::Initialize(const std::string& path,
|
||||
const std::string& target) {
|
||||
path_ = path;
|
||||
target_ = target;
|
||||
// TODO(gibbed): kernel_state_->RegisterSymbolicLink(this);
|
||||
}
|
||||
|
||||
bool XSymbolicLink::Save(ByteStream* stream) {
|
||||
if (!SaveObject(stream)) {
|
||||
return false;
|
||||
}
|
||||
stream->Write(path_);
|
||||
stream->Write(target_);
|
||||
return true;
|
||||
}
|
||||
|
||||
object_ref<XSymbolicLink> XSymbolicLink::Restore(KernelState* kernel_state,
|
||||
ByteStream* stream) {
|
||||
auto symlink = new XSymbolicLink();
|
||||
symlink->kernel_state_ = kernel_state;
|
||||
if (!symlink->RestoreObject(stream)) {
|
||||
delete symlink;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
auto path = stream->Read<std::string>();
|
||||
auto target = stream->Read<std::string>();
|
||||
symlink->Initialize(path, target);
|
||||
|
||||
return object_ref<XSymbolicLink>(symlink);
|
||||
}
|
||||
|
||||
} // namespace kernel
|
||||
} // namespace xe
|
||||
50
src/xenia/kernel/xsymboliclink.h
Normal file
50
src/xenia/kernel/xsymboliclink.h
Normal file
@@ -0,0 +1,50 @@
|
||||
/**
|
||||
******************************************************************************
|
||||
* Xenia : Xbox 360 Emulator Research Project *
|
||||
******************************************************************************
|
||||
* Copyright 2013 Ben Vanik. All rights reserved. *
|
||||
* Released under the BSD license - see LICENSE in the root for more details. *
|
||||
******************************************************************************
|
||||
*/
|
||||
|
||||
#ifndef XENIA_KERNEL_XSYMBOLICLINK_H_
|
||||
#define XENIA_KERNEL_XSYMBOLICLINK_H_
|
||||
|
||||
#include <memory>
|
||||
#include <unordered_map>
|
||||
|
||||
#include "xenia/base/mutex.h"
|
||||
#include "xenia/base/threading.h"
|
||||
#include "xenia/kernel/xobject.h"
|
||||
#include "xenia/xbox.h"
|
||||
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
class XSymbolicLink : public XObject {
|
||||
public:
|
||||
static const Type kType = kTypeSymbolicLink;
|
||||
|
||||
explicit XSymbolicLink(KernelState* kernel_state);
|
||||
~XSymbolicLink() override;
|
||||
|
||||
void Initialize(const std::string& path, const std::string& target);
|
||||
|
||||
bool Save(ByteStream* stream) override;
|
||||
static object_ref<XSymbolicLink> Restore(KernelState* kernel_state,
|
||||
ByteStream* stream);
|
||||
|
||||
const std ::string& path() const { return path_; }
|
||||
const std ::string& target() const { return target_; }
|
||||
|
||||
private:
|
||||
XSymbolicLink();
|
||||
|
||||
std::string path_;
|
||||
std::string target_;
|
||||
};
|
||||
|
||||
} // namespace kernel
|
||||
} // namespace xe
|
||||
|
||||
#endif // XENIA_KERNEL_XSYMBOLICLINK_H_
|
||||
@@ -49,13 +49,13 @@ using xe::cpu::ppc::PPCOpcode;
|
||||
uint32_t next_xthread_id_ = 0;
|
||||
|
||||
XThread::XThread(KernelState* kernel_state)
|
||||
: XObject(kernel_state, kTypeThread), guest_thread_(true) {}
|
||||
: XObject(kernel_state, kType), guest_thread_(true) {}
|
||||
|
||||
XThread::XThread(KernelState* kernel_state, uint32_t stack_size,
|
||||
uint32_t xapi_thread_startup, uint32_t start_address,
|
||||
uint32_t start_context, uint32_t creation_flags,
|
||||
bool guest_thread, bool main_thread)
|
||||
: XObject(kernel_state, kTypeThread),
|
||||
: XObject(kernel_state, kType),
|
||||
thread_id_(++next_xthread_id_),
|
||||
guest_thread_(guest_thread),
|
||||
main_thread_(main_thread),
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
namespace xe {
|
||||
namespace kernel {
|
||||
|
||||
XTimer::XTimer(KernelState* kernel_state) : XObject(kernel_state, kTypeTimer) {}
|
||||
XTimer::XTimer(KernelState* kernel_state) : XObject(kernel_state, kType) {}
|
||||
|
||||
XTimer::~XTimer() = default;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user