mirror of
https://github.com/citra-emu/citra.git
synced 2024-11-30 09:20:05 +00:00
Kernel: Implemented SharedMemory Kernel Object
HID: Added support for button input QT: Added dialogue for remapping keys
This commit is contained in:
parent
280d7af35d
commit
2a8cfe3ebb
@ -7,6 +7,7 @@ set(SRCS
|
||||
debugger/ramview.cpp
|
||||
debugger/registers.cpp
|
||||
hotkeys.cpp
|
||||
key_bindings.cpp
|
||||
main.cpp
|
||||
config/controller_config.cpp
|
||||
config/controller_config_util.cpp)
|
||||
@ -17,11 +18,13 @@ set (HEADERS
|
||||
debugger/ramview.hxx
|
||||
debugger/registers.hxx
|
||||
hotkeys.hxx
|
||||
key_bindings.hxx
|
||||
main.hxx
|
||||
ui_callstack.h
|
||||
ui_controller_config.h
|
||||
ui_disassembler.h
|
||||
ui_hotkeys.h
|
||||
ui_key_bindings.h
|
||||
ui_main.h
|
||||
ui_registers.h
|
||||
version.h
|
||||
@ -33,6 +36,7 @@ qt4_wrap_ui(UI_HDRS
|
||||
debugger/disassembler.ui
|
||||
debugger/registers.ui
|
||||
hotkeys.ui
|
||||
key_bindings.ui
|
||||
main.ui
|
||||
config/controller_config.ui)
|
||||
|
||||
@ -45,6 +49,7 @@ qt4_wrap_cpp(MOC_SRCS
|
||||
debugger/registers.hxx
|
||||
debugger/ramview.hxx
|
||||
hotkeys.hxx
|
||||
key_bindings.hxx
|
||||
main.hxx
|
||||
config/controller_config.hxx
|
||||
config/controller_config_util.hxx)
|
||||
|
@ -3,10 +3,13 @@
|
||||
|
||||
#include "common/common.h"
|
||||
#include "bootmanager.hxx"
|
||||
#include "key_bindings.hxx"
|
||||
|
||||
|
||||
#include "core/core.h"
|
||||
#include "core/loader.h"
|
||||
#include "core/hw/hw.h"
|
||||
#include "core/hw/hid.h"
|
||||
|
||||
#include "video_core/video_core.h"
|
||||
|
||||
@ -119,6 +122,8 @@ GRenderWindow::GRenderWindow(QWidget* parent) : QWidget(parent), emu_thread(this
|
||||
setLayout(layout);
|
||||
|
||||
BackupGeometry();
|
||||
|
||||
buttonReg = 0x0;
|
||||
}
|
||||
|
||||
GRenderWindow::~GRenderWindow()
|
||||
@ -192,12 +197,17 @@ void GRenderWindow::keyPressEvent(QKeyEvent* event)
|
||||
/*
|
||||
bool key_processed = false;
|
||||
for (unsigned int channel = 0; channel < 4 && controller_interface(); ++channel)
|
||||
if (controller_interface()->SetControllerStatus(channel, event->key(), input_common::GCController::PRESSED))
|
||||
key_processed = true;
|
||||
if (controller_interface()->SetControllerStatus(channel, event->key(), input_common::GCController::PRESSED))
|
||||
key_processed = true;
|
||||
|
||||
if (!key_processed)
|
||||
QWidget::keyPressEvent(event);
|
||||
QWidget::keyPressEvent(event);
|
||||
*/
|
||||
|
||||
|
||||
buttonReg |= GetKeyBinding(event);
|
||||
HID::SetButtonReg(buttonReg);
|
||||
return;
|
||||
}
|
||||
|
||||
void GRenderWindow::keyReleaseEvent(QKeyEvent* event)
|
||||
@ -211,4 +221,7 @@ void GRenderWindow::keyReleaseEvent(QKeyEvent* event)
|
||||
if (!key_processed)
|
||||
QWidget::keyPressEvent(event);
|
||||
*/
|
||||
|
||||
buttonReg &= 0xffffffff ^ GetKeyBinding(event);
|
||||
HID::SetButtonReg(buttonReg);
|
||||
}
|
@ -1,5 +1,6 @@
|
||||
#include <QThread>
|
||||
#include <QGLWidget>
|
||||
#include <map>
|
||||
#include "common/common.h"
|
||||
#include "common/emu_window.h"
|
||||
|
||||
@ -109,4 +110,6 @@ private:
|
||||
EmuThread emu_thread;
|
||||
|
||||
QByteArray geometry;
|
||||
|
||||
u32 buttonReg;
|
||||
};
|
||||
|
@ -137,6 +137,7 @@
|
||||
<ClCompile Include="debugger\ramview.cpp" />
|
||||
<ClCompile Include="bootmanager.cpp" />
|
||||
<ClCompile Include="hotkeys.cpp" />
|
||||
<ClCompile Include="key_bindings.cpp" />
|
||||
<ClCompile Include="main.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
@ -152,6 +153,7 @@
|
||||
<MOC Include="debugger\registers.hxx" />
|
||||
<MOC Include="bootmanager.hxx" />
|
||||
<MOC Include="hotkeys.hxx" />
|
||||
<MOC Include="key_bindings.hxx" />
|
||||
<MOC Include="main.hxx" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
@ -176,6 +178,7 @@
|
||||
<UIC Include="debugger\registers.ui" />
|
||||
<UIC Include="debugger\disassembler.ui" />
|
||||
<UIC Include="hotkeys.ui" />
|
||||
<UIC Include="key_bindings.ui" />
|
||||
<UIC Include="main.ui" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
@ -51,6 +51,7 @@
|
||||
<ClCompile Include="debugger\registers.cpp">
|
||||
<Filter>debugger</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="key_bindings.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<MOC Include="..\..\externals\qhexedit\commands.h">
|
||||
@ -86,6 +87,7 @@
|
||||
<MOC Include="debugger\registers.hxx">
|
||||
<Filter>debugger</Filter>
|
||||
</MOC>
|
||||
<MOC Include="key_bindings.hxx" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="version.h" />
|
||||
@ -111,6 +113,7 @@
|
||||
<UIC Include="debugger\registers.ui">
|
||||
<Filter>debugger</Filter>
|
||||
</UIC>
|
||||
<UIC Include="key_bindings.ui" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="CMakeLists.txt" />
|
||||
|
@ -17,6 +17,7 @@ GPUCommandListModel::GPUCommandListModel(QObject* parent) : QAbstractItemModel(p
|
||||
QModelIndex GPUCommandListModel::index(int row, int column, const QModelIndex& parent) const
|
||||
{
|
||||
TreeItem* item;
|
||||
TreeItem* internal;
|
||||
|
||||
if (!parent.isValid()) {
|
||||
item = root_item;
|
||||
@ -24,7 +25,13 @@ QModelIndex GPUCommandListModel::index(int row, int column, const QModelIndex& p
|
||||
item = (TreeItem*)parent.internalPointer();
|
||||
}
|
||||
|
||||
return createIndex(row, column, item->children[row]);
|
||||
if (item->children.size() <= row) {
|
||||
internal = item;
|
||||
}
|
||||
else { internal = item->children[row]; }
|
||||
|
||||
|
||||
return createIndex(row, column, internal);
|
||||
}
|
||||
|
||||
QModelIndex GPUCommandListModel::parent(const QModelIndex& child) const
|
||||
|
143
src/citra_qt/key_bindings.cpp
Normal file
143
src/citra_qt/key_bindings.cpp
Normal file
@ -0,0 +1,143 @@
|
||||
#include <QKeySequence>
|
||||
#include <QStyledItemDelegate>
|
||||
#include <QSettings>
|
||||
#include <QKeyEvent>
|
||||
#include "key_bindings.hxx"
|
||||
#include <map>
|
||||
#include "core/hw/hid.h"
|
||||
|
||||
typedef std::map<QKeySequence, HID::PAD> BindingsMap;
|
||||
|
||||
BindingsMap bindings;
|
||||
|
||||
|
||||
typedef std::map<HID::PAD, QKeySequence> ReverseBindingsMap;
|
||||
|
||||
ReverseBindingsMap reverseBindings;
|
||||
|
||||
|
||||
typedef std::map<HID::PAD, QString> NameMap;
|
||||
|
||||
NameMap names;
|
||||
|
||||
typedef std::map<QString, HID::PAD> ReverseNameMap;
|
||||
|
||||
ReverseNameMap reverseNames;
|
||||
|
||||
void SaveKeyBindings(QSettings& settings)
|
||||
{
|
||||
settings.beginGroup("KeyBindings");
|
||||
|
||||
for (BindingsMap::iterator group = bindings.begin(); group != bindings.end(); ++group)
|
||||
{
|
||||
settings.setValue(group->first.toString(), group->second);
|
||||
settings.endGroup();
|
||||
}
|
||||
settings.endGroup();
|
||||
}
|
||||
|
||||
void LoadKeyBindings(QSettings& settings)
|
||||
{
|
||||
settings.beginGroup("KeyBindings");
|
||||
|
||||
// Make sure NOT to use a reference here because it would become invalid once we call beginGroup()
|
||||
QStringList keys = settings.allKeys();
|
||||
for (QList<QString>::iterator key = keys.begin(); key != keys.end(); ++key)
|
||||
{
|
||||
settings.beginGroup(*key);
|
||||
QKeySequence keyseq = QKeySequence::fromString(settings.value("").toString());
|
||||
}
|
||||
|
||||
settings.endGroup();
|
||||
}
|
||||
|
||||
HID::PAD GetKeyBinding(QKeyEvent * event)
|
||||
{
|
||||
QKeySequence keySeq = QKeySequence(event->text());
|
||||
return bindings[keySeq];
|
||||
}
|
||||
|
||||
void RegisterKeyBinding(const QKeySequence keySeq, const HID::PAD pad)
|
||||
{
|
||||
bindings[keySeq] = pad;
|
||||
reverseBindings[pad] = keySeq;
|
||||
}
|
||||
|
||||
void createNameMap() {
|
||||
for (int i = 0; i < HID::numPadItems; i++){
|
||||
names[(HID::PAD)(1 << i)] = QString(HID::PAD_NAMES[i]);
|
||||
reverseNames[QString(HID::PAD_NAMES[i])] = (HID::PAD)(1 << i);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void setDefaultKeyBindings() {
|
||||
RegisterKeyBinding(QKeySequence("Y"), HID::PAD::PAD_A);
|
||||
RegisterKeyBinding(QKeySequence("H"), HID::PAD::PAD_B);
|
||||
RegisterKeyBinding(QKeySequence("Z"), HID::PAD::PAD_SELECT);
|
||||
RegisterKeyBinding(QKeySequence("X"), HID::PAD::PAD_START);
|
||||
|
||||
RegisterKeyBinding(QKeySequence("W"), HID::PAD::PAD_UP);
|
||||
RegisterKeyBinding(QKeySequence("A"), HID::PAD::PAD_LEFT);
|
||||
RegisterKeyBinding(QKeySequence("S"), HID::PAD::PAD_DOWN);
|
||||
RegisterKeyBinding(QKeySequence("D"), HID::PAD::PAD_RIGHT);
|
||||
|
||||
RegisterKeyBinding(QKeySequence("6"), HID::PAD::PAD_R);
|
||||
RegisterKeyBinding(QKeySequence("7"), HID::PAD::PAD_L);
|
||||
RegisterKeyBinding(QKeySequence("U"), HID::PAD::PAD_X);
|
||||
RegisterKeyBinding(QKeySequence("J"), HID::PAD::PAD_Y);
|
||||
|
||||
}
|
||||
|
||||
//class makes single columns uneditable
|
||||
class NoEditDelegate : public QStyledItemDelegate {
|
||||
public:
|
||||
NoEditDelegate(QObject* parent = 0) : QStyledItemDelegate(parent) {}
|
||||
virtual QWidget* createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const {
|
||||
return 0;
|
||||
}
|
||||
};
|
||||
|
||||
void GKeyBindingsDialog::updateItem(QTreeWidgetItem * item, int column) {
|
||||
bindings[item->text(1)] = reverseNames[item->text(0)]; //TODO: sanitise
|
||||
reverseBindings[reverseNames[item->text(0)]] = item->text(1);
|
||||
return;
|
||||
}
|
||||
|
||||
GKeyBindingsDialog::GKeyBindingsDialog(QWidget* parent) : QDialog(parent)
|
||||
{
|
||||
ui.setupUi(this);
|
||||
|
||||
createNameMap();
|
||||
|
||||
for (NameMap::iterator key = names.begin(); key != names.end(); ++key)
|
||||
{
|
||||
QKeySequence keySeq = reverseBindings[key->first];
|
||||
QStringList columns;
|
||||
columns << key->second << keySeq.toString();
|
||||
QTreeWidgetItem* item = new QTreeWidgetItem(columns);
|
||||
item->setFlags(Qt::ItemIsEnabled | Qt::ItemIsEditable | Qt::ItemIsSelectable);
|
||||
ui.treeWidget->addTopLevelItem(item);
|
||||
|
||||
}
|
||||
// TODO: Make context configurable as well (hiding the column for now)
|
||||
|
||||
ui.treeWidget->setEditTriggers(
|
||||
QAbstractItemView::EditKeyPressed
|
||||
| QAbstractItemView::SelectedClicked
|
||||
| QAbstractItemView::AnyKeyPressed
|
||||
);
|
||||
connect(
|
||||
this, SIGNAL(itemDoubleClicked(QTreeWidgetItem*, int)),
|
||||
this, SLOT(OnMouseDoubleClicked(QTreeWidgetItem*, int))
|
||||
);
|
||||
ui.treeWidget->setColumnCount(2);
|
||||
|
||||
ui.treeWidget->resizeColumnToContents(0);
|
||||
ui.treeWidget->resizeColumnToContents(1);
|
||||
|
||||
connect(ui.treeWidget, SIGNAL(itemChanged(QTreeWidgetItem *, int)),
|
||||
this, SLOT(updateItem(QTreeWidgetItem *, int)));
|
||||
ui.treeWidget->setItemDelegateForColumn(0, new NoEditDelegate(this));
|
||||
|
||||
}
|
62
src/citra_qt/key_bindings.hxx
Normal file
62
src/citra_qt/key_bindings.hxx
Normal file
@ -0,0 +1,62 @@
|
||||
#include <QDialog>
|
||||
#include "ui_key_bindings.h"
|
||||
#include "core/hw/hid.h"
|
||||
|
||||
|
||||
|
||||
class QSettings;
|
||||
|
||||
/**
|
||||
* Register a hotkey.
|
||||
*
|
||||
* @param key Keyboard button
|
||||
* @param pad Name of the pad
|
||||
*/
|
||||
|
||||
void RegisterKeyBinding(const QKeySequence keySeq, const HID::PAD pad);
|
||||
|
||||
|
||||
/**
|
||||
* Saves all key bindings to the settings file.
|
||||
*
|
||||
*
|
||||
*/
|
||||
void SaveKeyBindings(QSettings& settings);
|
||||
|
||||
|
||||
/**
|
||||
* Get PAD associated with key event
|
||||
*
|
||||
*
|
||||
*/
|
||||
HID::PAD GetKeyBinding(QKeyEvent * event);
|
||||
|
||||
/**
|
||||
* Loads key bindings from the settings file.
|
||||
*
|
||||
*
|
||||
*/
|
||||
void LoadKeyBindings(QSettings& settings);
|
||||
|
||||
|
||||
/**
|
||||
* Sets default key bindings.
|
||||
*
|
||||
*
|
||||
*/
|
||||
void setDefaultKeyBindings();
|
||||
|
||||
|
||||
class GKeyBindingsDialog : public QDialog
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
GKeyBindingsDialog(QWidget* parent = NULL);
|
||||
|
||||
private:
|
||||
Ui::key_bindings ui;
|
||||
|
||||
private slots:
|
||||
void updateItem(QTreeWidgetItem * item, int column);
|
||||
};
|
89
src/citra_qt/key_bindings.ui
Normal file
89
src/citra_qt/key_bindings.ui
Normal file
@ -0,0 +1,89 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>key_bindings</class>
|
||||
<widget class="QDialog" name="key_bindings">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>363</width>
|
||||
<height>388</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Key Bindings</string>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
<item>
|
||||
<widget class="QTreeWidget" name="treeWidget">
|
||||
<property name="selectionBehavior">
|
||||
<enum>QAbstractItemView::SelectItems</enum>
|
||||
</property>
|
||||
<property name="headerHidden">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<column>
|
||||
<property name="text">
|
||||
<string>Action</string>
|
||||
</property>
|
||||
</column>
|
||||
<column>
|
||||
<property name="text">
|
||||
<string>Key</string>
|
||||
</property>
|
||||
</column>
|
||||
<column>
|
||||
<property name="text">
|
||||
<string>Pad</string>
|
||||
</property>
|
||||
</column>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QDialogButtonBox" name="buttonBox">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="standardButtons">
|
||||
<set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok|QDialogButtonBox::Reset</set>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<resources/>
|
||||
<connections>
|
||||
<connection>
|
||||
<sender>buttonBox</sender>
|
||||
<signal>accepted()</signal>
|
||||
<receiver>key_bindings</receiver>
|
||||
<slot>accept()</slot>
|
||||
<hints>
|
||||
<hint type="sourcelabel">
|
||||
<x>248</x>
|
||||
<y>254</y>
|
||||
</hint>
|
||||
<hint type="destinationlabel">
|
||||
<x>157</x>
|
||||
<y>274</y>
|
||||
</hint>
|
||||
</hints>
|
||||
</connection>
|
||||
<connection>
|
||||
<sender>buttonBox</sender>
|
||||
<signal>rejected()</signal>
|
||||
<receiver>key_bindings</receiver>
|
||||
<slot>reject()</slot>
|
||||
<hints>
|
||||
<hint type="sourcelabel">
|
||||
<x>316</x>
|
||||
<y>260</y>
|
||||
</hint>
|
||||
<hint type="destinationlabel">
|
||||
<x>286</x>
|
||||
<y>274</y>
|
||||
</hint>
|
||||
</hints>
|
||||
</connection>
|
||||
</connections>
|
||||
</ui>
|
@ -13,6 +13,7 @@
|
||||
|
||||
#include "bootmanager.hxx"
|
||||
#include "hotkeys.hxx"
|
||||
#include "key_bindings.hxx"
|
||||
|
||||
//debugger
|
||||
#include "debugger/disassembler.hxx"
|
||||
@ -92,7 +93,8 @@ GMainWindow::GMainWindow()
|
||||
connect(ui.action_Pause, SIGNAL(triggered()), this, SLOT(OnPauseGame()));
|
||||
connect(ui.action_Stop, SIGNAL(triggered()), this, SLOT(OnStopGame()));
|
||||
connect(ui.action_Popout_Window_Mode, SIGNAL(triggered(bool)), this, SLOT(ToggleWindowMode()));
|
||||
connect(ui.action_Hotkeys, SIGNAL(triggered()), this, SLOT(OnOpenHotkeysDialog()));
|
||||
connect(ui.action_Hotkeys, SIGNAL(triggered()), this, SLOT(OnOpenHotkeysDialog()));\
|
||||
connect(ui.action_Key_Bindings, SIGNAL(triggered()), this, SLOT(OnOpenKeyBindingsDialog()));
|
||||
|
||||
// BlockingQueuedConnection is important here, it makes sure we've finished refreshing our views before the CPU continues
|
||||
connect(&render_window->GetEmuThread(), SIGNAL(CPUStepped()), disasmWidget, SLOT(OnCPUStepped()), Qt::BlockingQueuedConnection);
|
||||
@ -107,6 +109,11 @@ GMainWindow::GMainWindow()
|
||||
connect(GetHotkey("Main Window", "Load File", this), SIGNAL(activated()), this, SLOT(OnMenuLoadFile()));
|
||||
connect(GetHotkey("Main Window", "Start Emulation", this), SIGNAL(activated()), this, SLOT(OnStartGame()));
|
||||
|
||||
// Setup key bindings
|
||||
setDefaultKeyBindings();
|
||||
LoadKeyBindings(settings);
|
||||
|
||||
|
||||
setWindowTitle(render_window->GetWindowTitle().c_str());
|
||||
|
||||
show();
|
||||
@ -199,6 +206,13 @@ void GMainWindow::OnOpenHotkeysDialog()
|
||||
}
|
||||
|
||||
|
||||
void GMainWindow::OnOpenKeyBindingsDialog()
|
||||
{
|
||||
GKeyBindingsDialog dialog(this);
|
||||
dialog.exec();
|
||||
}
|
||||
|
||||
|
||||
void GMainWindow::ToggleWindowMode()
|
||||
{
|
||||
bool enable = ui.action_Popout_Window_Mode->isChecked();
|
||||
|
@ -41,6 +41,7 @@ private slots:
|
||||
void OnMenuLoadFile();
|
||||
void OnMenuLoadSymbolMap();
|
||||
void OnOpenHotkeysDialog();
|
||||
void OnOpenKeyBindingsDialog();
|
||||
void OnConfigure();
|
||||
void ToggleWindowMode();
|
||||
|
||||
|
@ -53,6 +53,7 @@
|
||||
<addaction name="action_Stop"/>
|
||||
<addaction name="separator"/>
|
||||
<addaction name="action_Configure"/>
|
||||
<addaction name="action_Key_Bindings"/>
|
||||
</widget>
|
||||
<widget class="QMenu" name="menu_View">
|
||||
<property name="title">
|
||||
@ -127,6 +128,11 @@
|
||||
<string>Configure &Hotkeys ...</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="action_Key_Bindings">
|
||||
<property name="text">
|
||||
<string>Set Key Bindings</string>
|
||||
</property>
|
||||
</action>
|
||||
<action name="action_Configure">
|
||||
<property name="text">
|
||||
<string>Configure ...</string>
|
||||
|
77
src/citra_qt/ui_key_bindings.h
Normal file
77
src/citra_qt/ui_key_bindings.h
Normal file
@ -0,0 +1,77 @@
|
||||
/********************************************************************************
|
||||
** Form generated from reading UI file 'key_bindings.ui'
|
||||
**
|
||||
** Created by: Qt User Interface Compiler version 4.8.6
|
||||
**
|
||||
** WARNING! All changes made in this file will be lost when recompiling UI file!
|
||||
********************************************************************************/
|
||||
|
||||
#ifndef UI_KEY_BINDINGS_H
|
||||
#define UI_KEY_BINDINGS_H
|
||||
|
||||
#include <QtCore/QVariant>
|
||||
#include <QtGui/QAction>
|
||||
#include <QtGui/QApplication>
|
||||
#include <QtGui/QButtonGroup>
|
||||
#include <QtGui/QDialog>
|
||||
#include <QtGui/QDialogButtonBox>
|
||||
#include <QtGui/QHeaderView>
|
||||
#include <QtGui/QTreeWidget>
|
||||
#include <QtGui/QVBoxLayout>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
|
||||
class Ui_key_bindings
|
||||
{
|
||||
public:
|
||||
QVBoxLayout *verticalLayout;
|
||||
QTreeWidget *treeWidget;
|
||||
QDialogButtonBox *buttonBox;
|
||||
|
||||
void setupUi(QDialog *key_bindings)
|
||||
{
|
||||
if (key_bindings->objectName().isEmpty())
|
||||
key_bindings->setObjectName(QString::fromUtf8("key_bindings"));
|
||||
key_bindings->resize(363, 388);
|
||||
verticalLayout = new QVBoxLayout(key_bindings);
|
||||
verticalLayout->setObjectName(QString::fromUtf8("verticalLayout"));
|
||||
treeWidget = new QTreeWidget(key_bindings);
|
||||
treeWidget->setObjectName(QString::fromUtf8("treeWidget"));
|
||||
treeWidget->setSelectionBehavior(QAbstractItemView::SelectItems);
|
||||
treeWidget->setHeaderHidden(false);
|
||||
|
||||
verticalLayout->addWidget(treeWidget);
|
||||
|
||||
buttonBox = new QDialogButtonBox(key_bindings);
|
||||
buttonBox->setObjectName(QString::fromUtf8("buttonBox"));
|
||||
buttonBox->setOrientation(Qt::Horizontal);
|
||||
buttonBox->setStandardButtons(QDialogButtonBox::Cancel|QDialogButtonBox::Ok|QDialogButtonBox::Reset);
|
||||
|
||||
verticalLayout->addWidget(buttonBox);
|
||||
|
||||
|
||||
retranslateUi(key_bindings);
|
||||
QObject::connect(buttonBox, SIGNAL(accepted()), key_bindings, SLOT(accept()));
|
||||
QObject::connect(buttonBox, SIGNAL(rejected()), key_bindings, SLOT(reject()));
|
||||
|
||||
QMetaObject::connectSlotsByName(key_bindings);
|
||||
} // setupUi
|
||||
|
||||
void retranslateUi(QDialog *key_bindings)
|
||||
{
|
||||
key_bindings->setWindowTitle(QApplication::translate("key_bindings", "Key Bindings", 0, QApplication::UnicodeUTF8));
|
||||
QTreeWidgetItem *___qtreewidgetitem = treeWidget->headerItem();
|
||||
___qtreewidgetitem->setText(2, QApplication::translate("key_bindings", "Pad", 0, QApplication::UnicodeUTF8));
|
||||
___qtreewidgetitem->setText(1, QApplication::translate("key_bindings", "Key", 0, QApplication::UnicodeUTF8));
|
||||
___qtreewidgetitem->setText(0, QApplication::translate("key_bindings", "Action", 0, QApplication::UnicodeUTF8));
|
||||
} // retranslateUi
|
||||
|
||||
};
|
||||
|
||||
namespace Ui {
|
||||
class key_bindings: public Ui_key_bindings {};
|
||||
} // namespace Ui
|
||||
|
||||
QT_END_NAMESPACE
|
||||
|
||||
#endif // UI_KEY_BINDINGS_H
|
@ -30,18 +30,18 @@
|
||||
<ClInclude Include="msg_handler.h" />
|
||||
<ClInclude Include="platform.h" />
|
||||
<ClInclude Include="register_set.h" />
|
||||
<ClInclude Include="scm_rev.h" />
|
||||
<ClInclude Include="std_condition_variable.h" />
|
||||
<ClInclude Include="std_mutex.h" />
|
||||
<ClInclude Include="std_thread.h" />
|
||||
<ClInclude Include="string_util.h" />
|
||||
<ClInclude Include="swap.h" />
|
||||
<ClInclude Include="symbols.h" />
|
||||
<ClInclude Include="thread.h" />
|
||||
<ClInclude Include="thread_queue_list.h" />
|
||||
<ClInclude Include="thunk.h" />
|
||||
<ClInclude Include="timer.h" />
|
||||
<ClInclude Include="utf8.h" />
|
||||
<ClInclude Include="symbols.h" />
|
||||
<ClInclude Include="scm_rev.h" />
|
||||
<ClInclude Include="thread_queue_list.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="break_points.cpp" />
|
||||
@ -56,14 +56,18 @@
|
||||
<ClCompile Include="memory_util.cpp" />
|
||||
<ClCompile Include="misc.cpp" />
|
||||
<ClCompile Include="msg_handler.cpp" />
|
||||
<ClCompile Include="scm_rev.cpp" />
|
||||
<ClCompile Include="string_util.cpp" />
|
||||
<ClCompile Include="symbols.cpp" />
|
||||
<ClCompile Include="thread.cpp" />
|
||||
<ClCompile Include="timer.cpp" />
|
||||
<ClCompile Include="utf8.cpp" />
|
||||
<ClCompile Include="symbols.cpp" />
|
||||
<ClCompile Include="scm_rev.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="CMakeLists.txt" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="scm_rev.cpp.in" />
|
||||
<None Include="scm_rev_gen.js" />
|
||||
</ItemGroup>
|
||||
</Project>
|
@ -67,6 +67,7 @@ enum LOG_TYPE {
|
||||
HW,
|
||||
TIME,
|
||||
NETPLAY,
|
||||
HID,
|
||||
|
||||
NUMBER_OF_LOGS // Must be last
|
||||
};
|
||||
|
@ -75,6 +75,7 @@ LogManager::LogManager()
|
||||
m_Log[LogTypes::ACTIONREPLAY] = new LogContainer("ActionReplay", "ActionReplay");
|
||||
m_Log[LogTypes::MEMCARD_MANAGER] = new LogContainer("MemCard Manager", "MemCard Manager");
|
||||
m_Log[LogTypes::NETPLAY] = new LogContainer("NETPLAY", "Netplay");
|
||||
m_Log[LogTypes::HID] = new LogContainer("HID", "Human Interface Devices");
|
||||
|
||||
m_fileLog = new FileLogListener(File::GetUserPath(F_MAINLOG_IDX).c_str());
|
||||
m_consoleLog = new ConsoleListener();
|
||||
|
@ -37,6 +37,7 @@ set(SRCS core.cpp
|
||||
hle/kernel/event.cpp
|
||||
hle/kernel/kernel.cpp
|
||||
hle/kernel/mutex.cpp
|
||||
hle/kernel/shared_memory.cpp
|
||||
hle/kernel/thread.cpp
|
||||
hle/service/apt.cpp
|
||||
hle/service/gsp.cpp
|
||||
@ -46,7 +47,8 @@ set(SRCS core.cpp
|
||||
hle/service/srv.cpp
|
||||
hw/gpu.cpp
|
||||
hw/hw.cpp
|
||||
hw/ndma.cpp)
|
||||
hw/ndma.cpp
|
||||
hw/hid.cpp)
|
||||
|
||||
set(HEADERS core.h
|
||||
core_timing.h
|
||||
@ -83,6 +85,7 @@ set(HEADERS core.h
|
||||
hle/svc.h
|
||||
hle/kernel/kernel.h
|
||||
hle/kernel/mutex.h
|
||||
hle/kernel/shared_memory.h
|
||||
hle/kernel/thread.h
|
||||
hle/function_wrappers.h
|
||||
hle/service/apt.h
|
||||
@ -92,6 +95,7 @@ set(HEADERS core.h
|
||||
hle/service/srv.h
|
||||
hw/gpu.h
|
||||
hw/hw.h
|
||||
hw/ndma.h)
|
||||
hw/ndma.h
|
||||
hw/hid.h)
|
||||
|
||||
add_library(core STATIC ${SRCS} ${HEADERS})
|
||||
|
@ -99,6 +99,9 @@
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<ClCompile />
|
||||
<ClCompile>
|
||||
<ObjectFileName>$(IntDir)%(RelativeDir)</ObjectFileName>
|
||||
</ClCompile>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
||||
<ClCompile />
|
||||
@ -106,6 +109,9 @@
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<ClCompile />
|
||||
<ClCompile>
|
||||
<ObjectFileName>$(IntDir)%(RelativeDir)</ObjectFileName>
|
||||
</ClCompile>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile />
|
||||
@ -120,6 +126,7 @@
|
||||
<FloatingPointModel>Fast</FloatingPointModel>
|
||||
<BufferSecurityCheck>false</BufferSecurityCheck>
|
||||
<EnableEnhancedInstructionSet>StreamingSIMDExtensions2</EnableEnhancedInstructionSet>
|
||||
<ObjectFileName>$(IntDir)%(RelativeDir)</ObjectFileName>
|
||||
</ClCompile>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||
@ -130,6 +137,9 @@
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
</Link>
|
||||
<ClCompile />
|
||||
<ClCompile>
|
||||
<ObjectFileName>$(IntDir)%(RelativeDir)</ObjectFileName>
|
||||
</ClCompile>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\common\common.vcxproj">
|
||||
@ -171,6 +181,7 @@
|
||||
<ClCompile Include="hle\kernel\event.cpp" />
|
||||
<ClCompile Include="hle\kernel\kernel.cpp" />
|
||||
<ClCompile Include="hle\kernel\mutex.cpp" />
|
||||
<ClCompile Include="hle\kernel\shared_memory.cpp" />
|
||||
<ClCompile Include="hle\kernel\thread.cpp" />
|
||||
<ClCompile Include="hle\service\apt.cpp" />
|
||||
<ClCompile Include="hle\service\gsp.cpp" />
|
||||
@ -180,6 +191,7 @@
|
||||
<ClCompile Include="hle\service\srv.cpp" />
|
||||
<ClCompile Include="hle\svc.cpp" />
|
||||
<ClCompile Include="hw\gpu.cpp" />
|
||||
<ClCompile Include="hw\hid.cpp" />
|
||||
<ClCompile Include="hw\hw.cpp" />
|
||||
<ClCompile Include="hw\ndma.cpp" />
|
||||
<ClCompile Include="loader.cpp" />
|
||||
@ -222,6 +234,7 @@
|
||||
<ClInclude Include="hle\kernel\event.h" />
|
||||
<ClInclude Include="hle\kernel\kernel.h" />
|
||||
<ClInclude Include="hle\kernel\mutex.h" />
|
||||
<ClInclude Include="hle\kernel\shared_memory.h" />
|
||||
<ClInclude Include="hle\kernel\thread.h" />
|
||||
<ClInclude Include="hle\service\apt.h" />
|
||||
<ClInclude Include="hle\service\gsp.h" />
|
||||
@ -231,6 +244,7 @@
|
||||
<ClInclude Include="hle\service\srv.h" />
|
||||
<ClInclude Include="hle\svc.h" />
|
||||
<ClInclude Include="hw\gpu.h" />
|
||||
<ClInclude Include="hw\hid.h" />
|
||||
<ClInclude Include="hw\hw.h" />
|
||||
<ClInclude Include="hw\ndma.h" />
|
||||
<ClInclude Include="loader.h" />
|
||||
|
@ -168,8 +168,8 @@
|
||||
<ClCompile Include="hle\kernel\event.cpp">
|
||||
<Filter>hle\kernel</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="hle\service\ndm.cpp">
|
||||
<Filter>hle\service</Filter>
|
||||
<ClCompile Include="hle\kernel\shared_memory.cpp">
|
||||
<Filter>hle\kernel</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
@ -307,6 +307,12 @@
|
||||
<ClInclude Include="hle\service\ndm.h">
|
||||
<Filter>hle\service</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="hw\hid.h">
|
||||
<Filter>hw</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="hle\kernel\shared_memory.h">
|
||||
<Filter>hle\kernel</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="CMakeLists.txt" />
|
||||
|
98
src/core/hle/kernel/shared_memory.cpp
Normal file
98
src/core/hle/kernel/shared_memory.cpp
Normal file
@ -0,0 +1,98 @@
|
||||
// Copyright 2014 Citra Emulator Project
|
||||
// Licensed under GPLv2
|
||||
// Refer to the license.txt file included.
|
||||
|
||||
#include <map>
|
||||
#include <vector>
|
||||
|
||||
#include "common/common.h"
|
||||
|
||||
#include "core/hle/kernel/kernel.h"
|
||||
#include "core/hle/kernel/thread.h"
|
||||
|
||||
namespace Kernel {
|
||||
|
||||
class SharedMemory : public Object {
|
||||
public:
|
||||
const char* GetTypeName() { return "SharedMemory"; }
|
||||
|
||||
static Kernel::HandleType GetStaticHandleType() { return Kernel::HandleType::SharedMemory; }
|
||||
Kernel::HandleType GetHandleType() const { return Kernel::HandleType::SharedMemory; }
|
||||
|
||||
//TODO: implement
|
||||
/**
|
||||
* Wait for kernel object to synchronize
|
||||
* @param wait Boolean wait set if current thread should wait as a result of sync operation
|
||||
* @return Result of operation, 0 on success, otherwise error code
|
||||
*/
|
||||
Result WaitSynchronization(bool* wait) {
|
||||
// TODO(bravia): ImplementMe
|
||||
return 0;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
inline void Read(T &var, const u32 addr);
|
||||
|
||||
template <typename T>
|
||||
inline void Write(T &var, const u32 addr);
|
||||
|
||||
u32 size;
|
||||
u8* mem_ptr = NULL;
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
SharedMemory* CreateSharedMemory(Handle& handle, u32 size) {
|
||||
SharedMemory* mem = new SharedMemory;
|
||||
handle = Kernel::g_object_pool.Create(mem);
|
||||
mem->size = size;
|
||||
return mem;
|
||||
}
|
||||
|
||||
Handle CreateSharedMemory(u32 size) {
|
||||
Handle handle;
|
||||
SharedMemory* mem = CreateSharedMemory(handle, size);
|
||||
return handle;
|
||||
}
|
||||
|
||||
u32 GetSharedMemorySize(Handle handle) {
|
||||
SharedMemory* mem = Kernel::g_object_pool.GetFast<SharedMemory>(handle);
|
||||
_assert_msg_(KERNEL, (mem != nullptr), "called, but mem is nullptr!");
|
||||
return mem->size;
|
||||
}
|
||||
|
||||
void SetSharedMemoryPointer(Handle handle, u8* ptr) {
|
||||
SharedMemory* mem = Kernel::g_object_pool.GetFast<SharedMemory>(handle);
|
||||
_assert_msg_(KERNEL, (mem != nullptr), "called, but mem is nullptr!");
|
||||
mem->mem_ptr = ptr;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
inline void ReadSharedMemory(Handle handle, T &var, const u32 addr) {
|
||||
SharedMemory* mem = Kernel::g_object_pool.GetFast<SharedMemory>(handle);
|
||||
_assert_msg_(KERNEL, (mem != nullptr), "called, but mem is nullptr!");
|
||||
if (mem->mem_ptr!=NULL)
|
||||
var = *((const T*)&mem->mem_ptr[addr & (mem->size - 1)]);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
inline void WriteSharedMemory(Handle handle, const T data, const u32 addr) {
|
||||
SharedMemory* mem = Kernel::g_object_pool.GetFast<SharedMemory>(handle);
|
||||
_assert_msg_(KERNEL, (mem != nullptr), "called, but mem is nullptr!");
|
||||
if (mem->mem_ptr != NULL)
|
||||
*(T*)&mem->mem_ptr[addr & (mem->size - 1)] = data;
|
||||
}
|
||||
|
||||
template void WriteSharedMemory<u64>(Handle handle, const u64 data, const u32 addr);
|
||||
template void WriteSharedMemory<u32>(Handle handle, const u32 data, const u32 addr);
|
||||
template void WriteSharedMemory<u16>(Handle handle, const u16 data, const u32 addr);
|
||||
template void WriteSharedMemory<u8>(Handle handle, const u8 data, const u32 addr);
|
||||
|
||||
template void ReadSharedMemory<u64>(Handle handle, u64 &var, const u32 addr);
|
||||
template void ReadSharedMemory<u32>(Handle handle, u32 &var, const u32 addr);
|
||||
template void ReadSharedMemory<u16>(Handle handle, u16 &var, const u32 addr);
|
||||
template void ReadSharedMemory<u8>(Handle handle, u8 &var, const u32 addr);
|
||||
|
||||
} // namespace
|
30
src/core/hle/kernel/shared_memory.h
Normal file
30
src/core/hle/kernel/shared_memory.h
Normal file
@ -0,0 +1,30 @@
|
||||
// Copyright 2014 Citra Emulator Project
|
||||
// Licensed under GPLv2
|
||||
// Refer to the license.txt file included.
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "common/common_types.h"
|
||||
|
||||
#include "core/hle/kernel/kernel.h"
|
||||
|
||||
namespace Kernel {
|
||||
|
||||
/**
|
||||
* Creates a shared memory object
|
||||
* @param handle Reference to handle for the newly created mutex
|
||||
* @param
|
||||
*/
|
||||
Handle CreateSharedMemory(u32 size);
|
||||
|
||||
u32 GetSharedMemorySize(Handle handle);
|
||||
|
||||
void SetSharedMemoryPointer(Handle handle, u8* ptr);
|
||||
|
||||
template <typename T>
|
||||
inline void ReadSharedMemory(Handle handle, T &var, const u32 addr);
|
||||
|
||||
template <typename T>
|
||||
inline void WriteSharedMemory(Handle handle, const T data, const u32 addr);
|
||||
|
||||
} // namespace
|
@ -9,6 +9,7 @@
|
||||
#include "core/mem_map.h"
|
||||
#include "core/hle/hle.h"
|
||||
#include "core/hle/kernel/event.h"
|
||||
#include "core/hle/kernel/shared_memory.h"
|
||||
#include "core/hle/service/gsp.h"
|
||||
|
||||
#include "core/hw/gpu.h"
|
||||
@ -20,6 +21,10 @@
|
||||
// Main graphics debugger object - TODO: Here is probably not the best place for this
|
||||
GraphicsDebugger g_debugger;
|
||||
|
||||
//Handle to irq memory
|
||||
Handle memIRQ;
|
||||
|
||||
|
||||
/// GSP shared memory GX command buffer header
|
||||
union GX_CmdBufferHeader {
|
||||
u32 hex;
|
||||
@ -121,6 +126,8 @@ void RegisterInterruptRelayQueue(Service::Interface* self) {
|
||||
Kernel::SetPermanentLock(event_handle, true);
|
||||
|
||||
cmd_buff[2] = g_thread_id; // ThreadID
|
||||
memIRQ = Kernel::CreateSharedMemory(0x1000); //page size for now
|
||||
cmd_buff[4] = memIRQ;
|
||||
}
|
||||
|
||||
|
||||
|
@ -6,14 +6,27 @@
|
||||
|
||||
#include "core/hle/hle.h"
|
||||
#include "core/hle/service/hid.h"
|
||||
#include "core/hle/kernel/shared_memory.h"
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Namespace HID_User
|
||||
|
||||
namespace HID_User {
|
||||
|
||||
Handle g_mem_ipc = NULL;
|
||||
|
||||
Handle GetMemIPCHandle() {
|
||||
return g_mem_ipc;
|
||||
}
|
||||
|
||||
void GetIPCHandles(Service::Interface* self) {
|
||||
u32* cmd_buff = Service::GetCommandBuffer();
|
||||
g_mem_ipc = Kernel::CreateSharedMemory(0x1000); //page size for now
|
||||
cmd_buff[3] = g_mem_ipc;
|
||||
}
|
||||
|
||||
const Interface::FunctionInfo FunctionTable[] = {
|
||||
{0x000A0000, nullptr, "GetIPCHandles"},
|
||||
{0x000A0000, GetIPCHandles, "GetIPCHandles" },
|
||||
{0x00110000, nullptr, "EnableAccelerometer"},
|
||||
{0x00130000, nullptr, "EnableGyroscopeLow"},
|
||||
{0x00150000, nullptr, "GetGyroscopeLowRawToDpsCoefficient"},
|
||||
|
@ -14,6 +14,8 @@
|
||||
|
||||
namespace HID_User {
|
||||
|
||||
Handle GetMemIPCHandle();
|
||||
|
||||
class Interface : public Service::Interface {
|
||||
public:
|
||||
|
||||
|
28
src/core/hw/hid.cpp
Normal file
28
src/core/hw/hid.cpp
Normal file
@ -0,0 +1,28 @@
|
||||
#include "hid.h"
|
||||
#include "core/hle/service/hid.h"
|
||||
#include "core/hle/kernel/shared_memory.h"
|
||||
|
||||
|
||||
namespace HID {
|
||||
|
||||
void SetButtonReg(u32 buttonData) {
|
||||
Handle sharedMem = HID_User::GetMemIPCHandle();
|
||||
if (sharedMem != NULL)
|
||||
Kernel::WriteSharedMemory(sharedMem, buttonData, OFFSET_BUTTONS);
|
||||
}
|
||||
|
||||
/// Update hardware
|
||||
void Update() {
|
||||
}
|
||||
|
||||
/// Initialize hardware
|
||||
void Init() {
|
||||
NOTICE_LOG(HID, "initialized OK");
|
||||
}
|
||||
|
||||
/// Shutdown hardware
|
||||
void Shutdown() {
|
||||
NOTICE_LOG(HID, "shutdown OK");
|
||||
}
|
||||
|
||||
}
|
67
src/core/hw/hid.h
Normal file
67
src/core/hw/hid.h
Normal file
@ -0,0 +1,67 @@
|
||||
#pragma once
|
||||
|
||||
#include "common/common_types.h"
|
||||
#include "core/mem_map.h"
|
||||
|
||||
|
||||
namespace HID {
|
||||
struct Registers {
|
||||
u32 buttons;
|
||||
//u32 pad1; etc...
|
||||
};
|
||||
|
||||
extern Registers g_regs;
|
||||
|
||||
enum {
|
||||
OFFSET_BUTTONS = 0x1c, //TODO: it works using the shared mem mapping with all homebrew tested, however the wiki states 0x10146000 as the paddr
|
||||
};
|
||||
|
||||
|
||||
enum {
|
||||
REG_BUTTONS = 0x1EC46000 //does not work due to confusion between shared mem and hardware IO
|
||||
};
|
||||
|
||||
const int numPadItems = 12; // figure out a better way :(
|
||||
|
||||
enum PAD {
|
||||
PAD_A = (1 << 0),
|
||||
PAD_B = (1 << 1),
|
||||
PAD_SELECT = (1 << 2),
|
||||
PAD_START = (1 << 3),
|
||||
PAD_RIGHT = (1 << 4),
|
||||
PAD_LEFT = (1 << 5),
|
||||
PAD_UP = (1 << 6),
|
||||
PAD_DOWN = (1 << 7),
|
||||
PAD_R = (1 << 8),
|
||||
PAD_L = (1 << 9),
|
||||
PAD_X = (1 << 10),
|
||||
PAD_Y = (1 << 11),
|
||||
};
|
||||
|
||||
char * const PAD_NAMES[] = {
|
||||
"PAD_A",
|
||||
"PAD_B",
|
||||
"PAD_SELECT",
|
||||
"PAD_START",
|
||||
"PAD_RIGHT",
|
||||
"PAD_LEFT",
|
||||
"PAD_UP",
|
||||
"PAD_DOWN",
|
||||
"PAD_R",
|
||||
"PAD_L",
|
||||
"PAD_X",
|
||||
"PAD_Y"
|
||||
};
|
||||
|
||||
void SetButtonReg(u32 buttonData);
|
||||
|
||||
/// Update hardware
|
||||
void Update();
|
||||
|
||||
/// Initialize hardware
|
||||
void Init();
|
||||
|
||||
/// Shutdown hardware
|
||||
void Shutdown();
|
||||
}
|
||||
|
@ -8,6 +8,8 @@
|
||||
#include "core/hw/hw.h"
|
||||
#include "core/hw/gpu.h"
|
||||
#include "core/hw/ndma.h"
|
||||
#include "core/hw/hid.h"
|
||||
|
||||
|
||||
namespace HW {
|
||||
|
||||
@ -89,12 +91,14 @@ template void Write<u8>(u32 addr, const u8 data);
|
||||
void Update() {
|
||||
GPU::Update();
|
||||
NDMA::Update();
|
||||
HID::Update();
|
||||
}
|
||||
|
||||
/// Initialize hardware
|
||||
void Init() {
|
||||
GPU::Init();
|
||||
NDMA::Init();
|
||||
HID::Init();
|
||||
NOTICE_LOG(HW, "initialized OK");
|
||||
}
|
||||
|
||||
|
@ -9,6 +9,8 @@
|
||||
#include "core/mem_map.h"
|
||||
#include "core/hw/hw.h"
|
||||
#include "hle/hle.h"
|
||||
#include "hle/kernel/kernel.h"
|
||||
#include "hle/kernel/shared_memory.h"
|
||||
#include "hle/config_mem.h"
|
||||
|
||||
namespace Memory {
|
||||
@ -71,8 +73,15 @@ inline void _Read(T &var, const u32 addr) {
|
||||
|
||||
// Shared memory
|
||||
} else if ((vaddr >= SHARED_MEMORY_VADDR) && (vaddr < SHARED_MEMORY_VADDR_END)) {
|
||||
var = *((const T*)&g_shared_mem[vaddr & SHARED_MEMORY_MASK]);
|
||||
|
||||
for (std::map<u32, MemoryBlock>::iterator it = g_shared_map.begin(); it != g_shared_map.end(); it++) {
|
||||
MemoryBlock block = it->second;
|
||||
if ((vaddr >= block.base_address) && (vaddr < block.GetVirtualAddress())) {
|
||||
Handle handle = block.handle;
|
||||
Kernel::ReadSharedMemory<T>(handle, var, addr);
|
||||
return;
|
||||
}
|
||||
}
|
||||
ERROR_LOG(MEMMAP, "Read from unknown shared mapping : Read%d @ 0x%08X", sizeof(var) * 8, vaddr);
|
||||
// System memory
|
||||
} else if ((vaddr >= SYSTEM_MEMORY_VADDR) && (vaddr < SYSTEM_MEMORY_VADDR_END)) {
|
||||
var = *((const T*)&g_system_mem[vaddr & SYSTEM_MEMORY_MASK]);
|
||||
@ -117,7 +126,15 @@ inline void _Write(u32 addr, const T data) {
|
||||
|
||||
// Shared memory
|
||||
} else if ((vaddr >= SHARED_MEMORY_VADDR) && (vaddr < SHARED_MEMORY_VADDR_END)) {
|
||||
*(T*)&g_shared_mem[vaddr & SHARED_MEMORY_MASK] = data;
|
||||
for (std::map<u32, MemoryBlock>::iterator it = g_shared_map.begin(); it != g_shared_map.end(); it++) {
|
||||
MemoryBlock block = it->second;
|
||||
if ((vaddr >= block.base_address) && (vaddr < block.base_address + block.size)) {
|
||||
Handle handle = block.handle;
|
||||
Kernel::WriteSharedMemory<T>(handle, data, addr);
|
||||
return;
|
||||
}
|
||||
}
|
||||
ERROR_LOG(MEMMAP, "Write to unknown shared mapping : Write%d 0x%08X @ 0x%08X", sizeof(data) * 8, data, vaddr);
|
||||
|
||||
// System memory
|
||||
} else if ((vaddr >= SYSTEM_MEMORY_VADDR) && (vaddr < SYSTEM_MEMORY_VADDR_END)) {
|
||||
@ -187,6 +204,7 @@ u32 MapBlock_Shared(u32 handle, u32 addr,u32 permissions) {
|
||||
MemoryBlock block;
|
||||
|
||||
block.handle = handle;
|
||||
block.size = Kernel::GetSharedMemorySize(handle);
|
||||
block.base_address = addr;
|
||||
block.permissions = permissions;
|
||||
|
||||
@ -194,9 +212,14 @@ u32 MapBlock_Shared(u32 handle, u32 addr,u32 permissions) {
|
||||
const MemoryBlock last_block = g_shared_map.rbegin()->second;
|
||||
block.address = last_block.address + last_block.size;
|
||||
}
|
||||
g_shared_map[block.GetVirtualAddress()] = block;
|
||||
|
||||
return block.GetVirtualAddress();
|
||||
u32 vaddr = block.GetVirtualAddress();
|
||||
|
||||
g_shared_map[vaddr] = block;
|
||||
|
||||
Kernel::SetSharedMemoryPointer(handle, &g_shared_mem[vaddr & SHARED_MEMORY_MASK]);
|
||||
|
||||
return vaddr;
|
||||
}
|
||||
|
||||
/**
|
||||
|
Loading…
Reference in New Issue
Block a user