1 #include <cstdarg>
2 #include <cstring>
3 #include <memory>
4 #include <vector>
5
6 #include "Common/CommonTypes.h"
7 #include "ext/armips/Core/Assembler.h"
8
9 #include "Common/Data/Encoding/Utf8.h"
10 #include "Core/Debugger/SymbolMap.h"
11 #include "Core/MemMapHelpers.h"
12 #include "Core/MIPS/JitCommon/JitCommon.h"
13 #include "Core/MIPS/MIPSAsm.h"
14
15 namespace MIPSAsm
16 {
17 static std::wstring errorText;
18
GetAssembleError()19 std::wstring GetAssembleError()
20 {
21 return errorText;
22 }
23
24 class PspAssemblerFile: public AssemblerFile
25 {
26 public:
PspAssemblerFile()27 PspAssemblerFile() {
28 address = 0;
29 }
30
open(bool onlyCheck)31 bool open(bool onlyCheck) override{ return true; };
close()32 void close() override { };
isOpen()33 bool isOpen() override { return true; };
write(void * data,size_t length)34 bool write(void* data, size_t length) override {
35 if (!Memory::IsValidAddress((u32)(address+length-1)))
36 return false;
37
38 Memory::Memcpy((u32)address, data, (u32)length, "Debugger");
39
40 // In case this is a delay slot or combined instruction, clear cache above it too.
41 if (MIPSComp::jit)
42 MIPSComp::jit->InvalidateCacheAt((u32)(address - 4),(int)length+4);
43
44 address += length;
45 return true;
46 }
getVirtualAddress()47 int64_t getVirtualAddress() override { return address; };
getPhysicalAddress()48 int64_t getPhysicalAddress() override { return getVirtualAddress(); };
getHeaderSize()49 int64_t getHeaderSize() override { return 0; }
seekVirtual(int64_t virtualAddress)50 bool seekVirtual(int64_t virtualAddress) override {
51 if (!Memory::IsValidAddress(virtualAddress))
52 return false;
53 address = virtualAddress;
54 return true;
55 }
seekPhysical(int64_t physicalAddress)56 bool seekPhysical(int64_t physicalAddress) override { return seekVirtual(physicalAddress); }
getFileName()57 const std::wstring &getFileName() override { return dummyWFilename_; }
58 private:
59 u64 address;
60 std::wstring dummyWFilename_;
61 };
62
MipsAssembleOpcode(const char * line,DebugInterface * cpu,u32 address)63 bool MipsAssembleOpcode(const char* line, DebugInterface* cpu, u32 address)
64 {
65 StringList errors;
66
67 wchar_t str[64];
68 swprintf(str,64,L".psp\n.org 0x%08X\n",address);
69
70 ArmipsArguments args;
71 args.mode = ArmipsMode::MEMORY;
72 args.content = str + ConvertUTF8ToWString(line);
73 args.silent = true;
74 args.memoryFile.reset(new PspAssemblerFile());
75 args.errorsResult = &errors;
76
77 if (g_symbolMap) {
78 g_symbolMap->GetLabels(args.labels);
79 }
80
81 errorText = L"";
82 if (!runArmips(args))
83 {
84 for (size_t i = 0; i < errors.size(); i++)
85 {
86 errorText += errors[i];
87 if (i != errors.size()-1)
88 errorText += L"\n";
89 }
90
91 return false;
92 }
93
94 return true;
95 }
96
97 } // namespace
98