Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/asmjit/asmjit.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/tools
diff options
context:
space:
mode:
authorkobalicek <kobalicek.petr@gmail.com>2017-02-09 16:15:08 +0300
committerkobalicek <kobalicek.petr@gmail.com>2017-02-09 16:15:08 +0300
commit43dbe48afc5a30f6f8eab2d6049fef92f7b30a3e (patch)
tree51ac539ecfd10caf3508d687b9f2ab834ebf4621 /tools
parenta984b508fc5677f960c17566fa1122c52dd7d840 (diff)
Added CodeCompiler::newSimilarReg, merged generate-xxx tools from next-wip branch, changed pcmpgtq to be in SSE4.2 group
Diffstat (limited to 'tools')
-rwxr-xr-x[-rw-r--r--]tools/configure-mac-xcode.sh0
-rwxr-xr-x[-rw-r--r--]tools/configure-unix-makefiles-dbg.sh0
-rwxr-xr-x[-rw-r--r--]tools/configure-unix-makefiles-rel.sh0
-rw-r--r--tools/generate-arm.js207
-rw-r--r--tools/generate-base.js488
-rw-r--r--tools/generate-x86.js997
6 files changed, 1087 insertions, 605 deletions
diff --git a/tools/configure-mac-xcode.sh b/tools/configure-mac-xcode.sh
index 45ad3ef..45ad3ef 100644..100755
--- a/tools/configure-mac-xcode.sh
+++ b/tools/configure-mac-xcode.sh
diff --git a/tools/configure-unix-makefiles-dbg.sh b/tools/configure-unix-makefiles-dbg.sh
index f127cf2..f127cf2 100644..100755
--- a/tools/configure-unix-makefiles-dbg.sh
+++ b/tools/configure-unix-makefiles-dbg.sh
diff --git a/tools/configure-unix-makefiles-rel.sh b/tools/configure-unix-makefiles-rel.sh
index 91e556b..91e556b 100644..100755
--- a/tools/configure-unix-makefiles-rel.sh
+++ b/tools/configure-unix-makefiles-rel.sh
diff --git a/tools/generate-arm.js b/tools/generate-arm.js
new file mode 100644
index 0000000..39843b0
--- /dev/null
+++ b/tools/generate-arm.js
@@ -0,0 +1,207 @@
+// [Generate-ARM]
+//
+// NOTE: This script relies on 'asmdb' package. Either install it by using
+// node.js package manager (npm) or by copying/symlinking the whole asmdb
+// directory as [asmjit]/tools/asmdb.
+"use strict";
+
+const base = require("./generate-base.js");
+const hasOwn = Object.prototype.hasOwnProperty;
+const kIndent = base.kIndent;
+const StringUtils = base.StringUtils;
+
+// ----------------------------------------------------------------------------
+// [ArmDB]
+// ----------------------------------------------------------------------------
+
+// Create the ARM database.
+const arm = base.asmdb.arm;
+const isa = new arm.ISA();
+
+console.log(
+ isa.query({
+ filter: function(inst) {
+ return !!inst.extensions.ASIMD;
+ }
+ })
+);
+
+//console.log(JSON.stringify(isa.instructionMap, null, 2));
+
+// ----------------------------------------------------------------------------
+// [GenUtils]
+// ----------------------------------------------------------------------------
+
+class GenUtils {
+ // Get a list of instructions based on `name` and optional `mode`.
+ static instsOf(name, mode) {
+ const insts = isa.query(name);
+ return !mode ? insts : insts.filter(function(inst) { return inst.arch === mode; });
+ }
+
+ static archOf(group) {
+ var t16Arch = false;
+ var t32Arch = false;
+ var a32Arch = false;
+ var a64Arch = false;
+
+ for (var i = 0; i < group.length; i++) {
+ const inst = group[i];
+ if (inst.encoding === "T16") t16Arch = true;
+ if (inst.encoding === "T32") t32Arch = true;
+ if (inst.encoding === "A32") a32Arch = true;
+ if (inst.encoding === "A64") a64Arch = true;
+ }
+
+ var s = (t16Arch && !t32Arch) ? "T16" :
+ (t32Arch && !t16Arch) ? "T32" :
+ (t16Arch && t32Arch) ? "Txx" : "---";
+ s += " ";
+ s += (a32Arch) ? "A32" : "---";
+ s += " ";
+ s += (a64Arch) ? "A64" : "---";
+
+ return `[${s}]`;
+ }
+
+ static featuresOf(group) {
+ const exts = Object.create(null);
+ for (var i = 0; i < group.length; i++) {
+ const inst = group[i];
+ for (var k in inst.extensions)
+ exts[k] = true;
+ }
+ const arr = Object.keys(exts);
+ arr.sort();
+ return arr;
+ }
+}
+
+// ----------------------------------------------------------------------------
+// [ArmGenerator]
+// ----------------------------------------------------------------------------
+
+class ArmGenerator extends base.BaseGenerator {
+ constructor() {
+ super("Arm");
+
+ this.load([
+ "src/asmjit/arm/arminst.cpp",
+ "src/asmjit/arm/arminst.h"
+ ]);
+ }
+
+ // --------------------------------------------------------------------------
+ // [Parse]
+ // --------------------------------------------------------------------------
+
+ parse() {
+ this.addInst({
+ id: 0,
+ name: "",
+ enum: "None"
+ });
+
+ var names = isa.instructionNames;
+ for (var i = 0; i < names.length; i++) {
+ const name = names[i];
+
+ const enum_ = StringUtils.upFirst(name);
+ const insts = GenUtils.instsOf(names[i]);
+
+ this.addInst({
+ id : 0, // Instruction id (numeric value).
+ name : name, // Instruction name.
+ enum : enum_, // Instruction enum without `kId` prefix.
+
+ familyType : "kFamilyNone", // Family type.
+ familyIndex : 0, // Index to a family-specific data.
+
+ nameIndex : -1, // Instruction name-index.
+ commonIndex : -1
+ });
+ }
+
+ console.log("Number of Instructions: " + this.instArray.length);
+ }
+
+ // --------------------------------------------------------------------------
+ // [Generate]
+ // --------------------------------------------------------------------------
+
+ generate() {
+ // Order doesn't matter here.
+ this.generateIdData();
+ this.generateNameData();
+
+ // These must be last, and order matters.
+ this.generateCommonData();
+ this.generateInstData();
+
+ return this;
+ }
+
+ // --------------------------------------------------------------------------
+ // [Generate - CommonData]
+ // --------------------------------------------------------------------------
+
+ generateCommonData() {
+ const table = new base.IndexedArray();
+ for (var i = 0; i < this.instArray.length; i++) {
+ const inst = this.instArray[i];
+
+ const item = "{ " + StringUtils.padLeft("0", 1) + "}";
+ inst.commonIndex = table.addIndexed(item);
+ }
+
+ var s = `const ArmInst::CommonData ArmInstDB::commonData[] = {\n${StringUtils.format(table, kIndent, true)}\n};\n`;
+ return this.inject("commonData", StringUtils.disclaimer(s), table.length * 12);
+ }
+
+ // --------------------------------------------------------------------------
+ // [Generate - InstData]
+ // --------------------------------------------------------------------------
+
+ generateInstData() {
+ var s = StringUtils.format(this.instArray, "", false, function(inst) {
+ return "INST(" +
+ StringUtils.padLeft(inst.enum , 16) + ", " +
+ StringUtils.padLeft(inst.encoding , 23) + ", " +
+ StringUtils.padLeft(inst.opcode0 , 26) + ", " +
+ StringUtils.padLeft(inst.nameIndex , 4) + ", " +
+ StringUtils.padLeft(inst.commonIndex, 3) + ")";
+ }) + "\n";
+ return this.inject("instData", s, this.instArray.length * 12);
+ }
+
+ // --------------------------------------------------------------------------
+ // [Reimplement]
+ // --------------------------------------------------------------------------
+
+ getCommentOf(name) {
+ var insts = GenUtils.instsOf(name);
+ if (!insts) return "";
+
+ var features = GenUtils.featuresOf(insts);
+ var comment = GenUtils.archOf(insts);
+
+ if (features.length)
+ comment += " {" + features.join("|") + "}";
+
+ return comment;
+ }
+}
+
+// ----------------------------------------------------------------------------
+// [Main]
+// ----------------------------------------------------------------------------
+
+function main() {
+ const gen = new ArmGenerator();
+
+ gen.parse();
+ gen.generate();
+ gen.dumpTableSizes();
+ gen.save();
+}
+main();
diff --git a/tools/generate-base.js b/tools/generate-base.js
new file mode 100644
index 0000000..4b696ed
--- /dev/null
+++ b/tools/generate-base.js
@@ -0,0 +1,488 @@
+// [Generate-Base]
+"use strict";
+
+const fs = require("fs");
+const hasOwn = Object.prototype.hasOwnProperty;
+
+// ----------------------------------------------------------------------------
+// [asmdb]
+// ----------------------------------------------------------------------------
+
+const asmdb = (function() {
+ try {
+ // Prefer a local copy of 'asmdb' package if possible.
+ return require("./asmdb");
+ }
+ catch (ex) {
+ // Report a possible problem within a local asmdb.
+ if (ex.code !== "MODULE_NOT_FOUND")
+ throw ex;
+
+ // Okay, so global then...
+ return require("asmdb");
+ }
+})();
+exports.asmdb = asmdb;
+
+// ----------------------------------------------------------------------------
+// [Constants]
+// ----------------------------------------------------------------------------
+
+const kIndent = " ";
+const kJustify = 79;
+const kAsmJitRoot = "..";
+
+exports.kIndent = kIndent;
+exports.kJustify = kJustify;
+exports.kAsmJitRoot = kAsmJitRoot;
+
+// ----------------------------------------------------------------------------
+// [StringUtils]
+// ----------------------------------------------------------------------------
+
+function asString(x) { return String(x); }
+
+class StringUtils {
+ static trimLeft(s) {
+ return s.replace(/^\s+/, "");
+ }
+
+ static padLeft(s, n, x) {
+ if (!x) x = " ";
+
+ s = String(s);
+ if (s.length < n)
+ s += x.repeat(n - s.length);
+
+ return s;
+ }
+
+ static upFirst(s) {
+ if (!s) return "";
+ return s[0].toUpperCase() + s.substr(1);
+ }
+
+ static decToHex(n, nPad) {
+ var hex = Number(n < 0 ? 0x100000000 + n : n).toString(16);
+ while (nPad > hex.length)
+ hex = "0" + hex;
+ return "0x" + hex.toUpperCase();
+ }
+
+ static format(array, indent, showIndex, mapFn) {
+ if (!mapFn)
+ mapFn = asString;
+
+ var s = "";
+ const commentSize = showIndex ? String(array.length).length : 0;
+
+ for (var i = 0; i < array.length; i++) {
+ const last = i === array.length - 1;
+ s += `${indent}${mapFn(array[i])}`;
+
+ if (commentSize)
+ s += `${last ? " " : ","} // #${i}`;
+ else if (!last)
+ s += ",";
+
+ if (!last) s += "\n";
+ }
+
+ return s;
+ }
+
+ static arrayToMap(arr, value) {
+ if (value === undefined)
+ value = true;
+
+ const map = Object.create(null);
+ for (var i = 0; i < arr.length; i++)
+ map[arr[i]] = value;
+ return map;
+ }
+
+ static makeCxxArray(array, code, indent) {
+ if (!indent) indent = kIndent;
+ return `${code} = {\n${indent}` + array.join(`,\n${indent}`) + `\n};\n`;
+ }
+
+ static makeCxxArrayWithComment(array, code, indent) {
+ if (!indent) indent = kIndent;
+ var s = "";
+ for (var i = 0; i < array.length; i++) {
+ const last = i === array.length - 1;
+ s += indent + array[i].data +
+ (last ? " // " : ", // ") + StringUtils.padLeft(array[i].refs ? "#" + String(i) : "", 5) + array[i].comment + "\n";
+ }
+ return `${code} = {\n${s}};\n`;
+ }
+
+ static disclaimer(s) {
+ return "// ------------------- Automatically generated, do not edit -------------------\n" +
+ s +
+ "// ----------------------------------------------------------------------------\n";
+ }
+
+ static indent(s, indentation) {
+ var lines = s.split(/\r?\n/g);
+ if (indentation) {
+ for (var i = 0; i < lines.length; i++) {
+ var line = lines[i];
+ if (line) lines[i] = indentation + line;
+ }
+ }
+
+ return lines.join("\n");
+ }
+
+ static inject(s, start, end, code) {
+ var iStart = s.indexOf(start);
+ var iEnd = s.indexOf(end);
+
+ if (iStart === -1)
+ throw new Error(`Utils.inject(): Couldn't locate start mark '${start}'`);
+
+ if (iEnd === -1)
+ throw new Error(`Utils.inject(): Couldn't locate end mark '${end}'`);
+
+ var nIndent = 0;
+ while (iStart > 0 && s[iStart-1] === " ") {
+ iStart--;
+ nIndent++;
+ }
+
+ if (nIndent) {
+ const indentation = " ".repeat(nIndent);
+ code = StringUtils.indent(code, indentation) + indentation;
+ }
+
+ return s.substr(0, iStart + start.length + nIndent) + code + s.substr(iEnd);
+ }
+}
+exports.StringUtils = StringUtils;
+
+// ----------------------------------------------------------------------------
+// [IndexedArray]
+// ----------------------------------------------------------------------------
+
+class IndexedArray extends Array {
+ constructor() {
+ super();
+ this._index = Object.create(null);
+ }
+
+ addIndexed(element) {
+ const key = typeof element === "string" ? element : JSON.stringify(element);
+ var idx = this._index[key];
+
+ if (idx !== undefined)
+ return idx;
+
+ idx = this.length;
+ this._index[key] = idx;
+ this.push(element);
+ return idx;
+ }
+}
+exports.IndexedArray = IndexedArray;
+
+// ----------------------------------------------------------------------------
+// [IndexedString]
+// ----------------------------------------------------------------------------
+
+class IndexedString {
+ constructor() {
+ this.map = Object.create(null);
+ this.array = [];
+ this.size = -1;
+ }
+
+ add(s) {
+ this.map[s] = -1;
+ }
+
+ index() {
+ const map = this.map;
+ const array = this.array;
+ const partialMap = Object.create(null);
+
+ var k, kp;
+ var i, len;
+
+ // Create a map that will contain all keys and partial keys.
+ for (k in map) {
+ if (!k) {
+ partialMap[k] = k;
+ }
+ else {
+ for (i = 0, len = k.length; i < len; i++) {
+ kp = k.substr(i);
+ if (!hasOwn.call(partialMap, kp) || partialMap[kp].length < len)
+ partialMap[kp] = k;
+ }
+ }
+ }
+
+ // Create an array that will only contain keys that are needed.
+ for (k in map)
+ if (partialMap[k] === k)
+ array.push(k);
+ array.sort();
+
+ // Create valid offsets to the `array`.
+ var offMap = Object.create(null);
+ var offset = 0;
+
+ for (i = 0, len = array.length; i < len; i++) {
+ k = array[i];
+
+ offMap[k] = offset;
+ offset += k.length + 1;
+ }
+ this.size = offset;
+
+ // Assign valid offsets to `map`.
+ for (kp in map) {
+ k = partialMap[kp];
+ map[kp] = offMap[k] + k.length - kp.length;
+ }
+ }
+
+ format(indent, justify) {
+ if (this.size === -1)
+ throw new Error(`IndexedString.format(): not indexed yet, call index()`);
+
+ const array = this.array;
+ if (!justify) justify = 0;
+
+ var i;
+ var s = "";
+ var line = "";
+
+ for (i = 0; i < array.length; i++) {
+ const item = "\"" + array[i] + ((i !== array.length - 1) ? "\\0\"" : "\";");
+ const newl = line + (line ? " " : indent) + item;
+
+ if (newl.length <= justify) {
+ line = newl;
+ continue;
+ }
+ else {
+ s += line + "\n";
+ line = indent + item;
+ }
+ }
+
+ return s + line;
+ }
+
+ getSize() {
+ if (this.size === -1)
+ throw new Error(`IndexedString.getSize(): Not indexed yet, call index()`);
+ return this.size;
+ }
+
+ getIndex(k) {
+ if (this.size === -1)
+ throw new Error(`IndexedString.getIndex(): Not indexed yet, call index()`);
+
+ if (!hasOwn.call(this.map, k))
+ throw new Error(`IndexedString.getIndex(): Key '${k}' not found.`);
+
+ return this.map[k];
+ }
+}
+exports.IndexedString = IndexedString;
+
+// ----------------------------------------------------------------------------
+// [BaseGenerator]
+// ----------------------------------------------------------------------------
+
+class BaseGenerator {
+ constructor(arch) {
+ this.arch = arch;
+
+ this.instMap = Object.create(null);
+ this.instArray = [];
+
+ this.files = Object.create(null);
+ this.tableSizes = Object.create(null);
+ }
+
+ // --- File management ---
+ load(fileList) {
+ for (var i = 0; i < fileList.length; i++) {
+ const file = fileList[i];
+ const path = kAsmJitRoot + "/" + file;
+ const data = fs.readFileSync(path, "utf8").replace(/\r\n/g, "\n");
+
+ this.files[file] = {
+ prev: data,
+ data: data
+ };
+ }
+ return this;
+ }
+
+ save() {
+ for (var file in this.files) {
+ const obj = this.files[file];
+ if (obj.data !== obj.prev) {
+ const path = kAsmJitRoot + "/" + file;
+ console.log(`MODIFIED '${file}'`);
+
+ fs.writeFileSync(path + ".backup", obj.prev, "utf8");
+ fs.writeFileSync(path, obj.data, "utf8");
+ }
+ }
+ }
+
+ dataOf(file) {
+ const obj = this.files[file];
+ if (!obj)
+ throw new Error(`BaseGenerator.getData(): File ${file} not loaded`);
+ return obj.data;
+ }
+
+ // --- Instruction management ---
+ addInst(inst) {
+ inst.id = this.instArray.length;
+
+ this.instMap[inst.name] = inst;
+ this.instArray.push(inst);
+
+ return this;
+ }
+
+ // --- Code Injection ---
+ inject(key, str, size) {
+ const begin = "// ${" + key + ":Begin}\n";
+ const end = "// ${" + key + ":End}\n";
+
+ var done = false;
+ for (var file in this.files) {
+ const obj = this.files[file];
+ const data = obj.data;
+
+ if (data.indexOf(begin) !== -1) {
+ obj.data = StringUtils.inject(data, begin, end, str);
+ done = true;
+ break;
+ }
+ }
+
+ if (!done)
+ throw new Error(`Generator.inject(): Cannot find '${key}'`);
+
+ if (size)
+ this.tableSizes[key] = size;
+
+ return this;
+ }
+
+ // --- Independent Generators ---
+ generateIdData() {
+ const instArray = this.instArray;
+
+ var s = "";
+ for (var i = 0; i < instArray.length; i++) {
+ const inst = instArray[i];
+
+ var line = "kId" + inst.enum + (i ? "" : " = 0") + ",";
+ var comment = this.getCommentOf(inst.name);
+
+ if (comment)
+ line = StringUtils.padLeft(line, 37) + "// " + comment;
+
+ s += line + "\n";
+ }
+ s += "_kIdCount\n";
+
+ return this.inject("idData", s);
+ }
+
+ generateNameData() {
+ const arch = this.arch;
+ const none = `${arch}Inst::kIdNone`;
+
+ const instArray = this.instArray;
+ const instNames = new IndexedString();
+
+ const instFirst = new Array(26);
+ const instLast = new Array(26);
+
+ var maxLength = 0;
+ for (var i = 0; i < instArray.length; i++) {
+ const inst = instArray[i];
+ instNames.add(inst.name);
+ maxLength = Math.max(maxLength, inst.name.length);
+ }
+ instNames.index();
+
+ for (var i = 0; i < instArray.length; i++) {
+ const inst = instArray[i];
+ const name = inst.name;
+ const nameIndex = instNames.getIndex(name);
+
+ const index = name.charCodeAt(0) - 'a'.charCodeAt(0);
+ if (index < 0 || index >= 26)
+ throw new Error(`BaseGenerator.generateNameData(): Invalid lookup character '${name[0]}' of '${name}'`);
+
+ inst.nameIndex = nameIndex;
+ if (instFirst[index] === undefined)
+ instFirst[index] = `${arch}Inst::kId${inst.enum}`;
+ instLast[index] = `${arch}Inst::kId${inst.enum}`;
+ }
+
+ var s = "";
+ s += `const char ${arch}InstDB::nameData[] =\n${instNames.format(kIndent, kJustify)}\n`;
+ s += `\n`;
+
+ s += `enum {\n`;
+ s += ` k${arch}InstMaxLength = ${maxLength}\n`;
+ s += `};\n`;
+ s += `\n`;
+
+ s += `struct InstNameAZ {\n`;
+ s += ` uint16_t start;\n`;
+ s += ` uint16_t end;\n`;
+ s += `};\n`;
+ s += `\n`;
+
+ s += `static const InstNameAZ ${arch}InstNameAZ[26] = {\n`;
+ for (var i = 0; i < instFirst.length; i++) {
+ const firstId = instFirst[i] || none;
+ const lastId = instLast[i] || none;
+
+ s += ` { ${StringUtils.padLeft(firstId, 22)}, ${StringUtils.padLeft(lastId , 22)} + 1 }`;
+ if (i !== 26 - 1)
+ s += `,`;
+ s += `\n`;
+ }
+ s += `};\n`;
+
+ return this.inject("nameData", StringUtils.disclaimer(s), instNames.getSize() + 26 * 4);
+ }
+
+ // --- Reimplement ---
+ getCommentOf(name) {
+ throw new Error("BaseGenerator.getCommentOf(): Must be reimplemented");
+ }
+
+ // --- Miscellaneous ---
+ dumpTableSizes() {
+ const sizes = this.tableSizes;
+
+ var pad = 24;
+ var total = 0;
+
+ for (var name in sizes) {
+ const size = sizes[name];
+ total += size;
+ console.log(StringUtils.padLeft('Size of ' + name, pad) + ": " + size);
+ }
+
+ console.log(StringUtils.padLeft('Size of all tables', pad) + ": " + total);
+ }
+}
+exports.BaseGenerator = BaseGenerator;
diff --git a/tools/generate-x86.js b/tools/generate-x86.js
index 0a0cf7d..9c144e2 100644
--- a/tools/generate-x86.js
+++ b/tools/generate-x86.js
@@ -6,302 +6,94 @@
// by a linker to make all pointers the binary application/library uses valid.
// This approach decreases the final size of AsmJit binary and relocation data.
//
-// NOTE: This script now relies on 'asmdb' package. Either install it by using
-// node.js package manager (npm) or copy x86data.js and x86util.js files into
-// the asmjit/tools directory.
+// NOTE: This script relies on 'asmdb' package. Either install it by using
+// node.js package manager (npm) or by copying/symlinking the whole asmdb
+// directory as [asmjit]/tools/asmdb.
"use strict";
-const fs = require("fs");
+const base = require("./generate-base.js");
const hasOwn = Object.prototype.hasOwnProperty;
-
-const asmdb = (function() {
- try {
- // Prefer a local copy of 'asmdb' package if possible.
- return {
- x86data: require("./x86data.js"),
- x86util: require("./x86util.js")
- };
- }
- catch (ex) {
- // Okay, so global then...
- return require("asmdb.js");
- }
-})();
-
-// Special cases.
-const x86db = new asmdb.x86util.X86DataBase().addDefault();
-x86db.addInstructions([
- // Imul in [reg, imm] form is encoded as [reg, reg, imm].
- ["imul" , "r16, ib" , "RM" , "66 6B /r ib" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
- ["imul" , "r32, ib" , "RM" , "6B /r ib" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
- ["imul" , "r64, ib" , "RM" , "REX.W 6B /r ib" , "X64 OF=W SF=W ZF=U AF=U PF=U CF=W"],
- ["imul" , "r16, iw" , "RM" , "66 69 /r iw" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
- ["imul" , "r32, id" , "RM" , "69 /r id" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
- ["imul" , "r64, id" , "RM" , "REX.W 69 /r id" , "X64 OF=W SF=W ZF=U AF=U PF=U CF=W"]
-]);
-
-// ----------------------------------------------------------------------------
-// [Integration]
-// ----------------------------------------------------------------------------
-
-const kFileName = "../src/asmjit/x86/x86inst.cpp";
-const kIndent = " ";
-const kJustify = 79;
-const kX86InstPrefix = "X86Inst::kId";
-
-const kDisclaimerStart = "// ------------------- Automatically generated, do not edit -------------------\n";
-const kDisclaimerEnd = "// ----------------------------------------------------------------------------\n";
-
-// ----------------------------------------------------------------------------
-// [Utils]
-// ----------------------------------------------------------------------------
-
-class Utils {
- static upFirst(s) {
- if (!s) return "";
- return s[0].toUpperCase() + s.substr(1);
- }
-
- static trimLeft(s) {
- return s.replace(/^\s+/, "");
- }
-
- static padLeft(s, n, x) {
- if (!x) x = " ";
-
- s = String(s);
- if (s.length < n)
- s += x.repeat(n - s.length);
-
- return s;
- }
-
- static decToHex(n, nPad) {
- var hex = Number(n < 0 ? 0x100000000 + n : n).toString(16);
- while (nPad > hex.length)
- hex = "0" + hex;
- return "0x" + hex.toUpperCase();
- }
-
- static format(array, indent, showIndex, mapFn) {
- if (!mapFn)
- mapFn = function(x) { return String(x); }
-
- const commentSize = showIndex ? String(array.length).length : 0;
-
- var s = "";
- for (var i = 0; i < array.length; i++) {
- const last = i === array.length - 1;
- s += `${indent}${mapFn(array[i])}`;
-
- if (commentSize)
- s += `${last ? " " : ","} // #${i}`;
- else if (!last)
- s += ",";
-
- if (!last) s += "\n";
- }
- return s;
- }
-
- static inject(s, start, end, code) {
- var iStart = s.indexOf(start);
- var iEnd = s.indexOf(end);
-
- if (iStart === -1)
- throw new Error(`Utils.inject(): Couldn't locate start mark '${start}'`);
-
- if (iEnd === -1)
- throw new Error(`Utils.inject(): Couldn't locate end mark '${end}'`);
-
- return s.substr(0, iStart + start.length) + code + s.substr(iEnd);
- }
-}
-
-// ----------------------------------------------------------------------------
-// [IndexedArray]
-// ----------------------------------------------------------------------------
-
-class IndexedArray extends Array {
- constructor() {
- super();
- this._index = Object.create(null);
- }
-
- addIndexed(element) {
- const key = typeof element === "string" ? element : JSON.stringify(element);
- var idx = this._index[key];
-
- if (idx !== undefined)
- return idx;
-
- idx = this.length;
- this._index[key] = idx;
- this.push(element);
- return idx;
- }
-}
+const kIndent = base.kIndent;
+const StringUtils = base.StringUtils;
// ----------------------------------------------------------------------------
-// [IndexedString]
+// [X86DB]
// ----------------------------------------------------------------------------
-class IndexedString {
- constructor() {
- this.map = Object.create(null);
- this.array = [];
- this.size = -1;
- }
-
- add(s) {
- this.map[s] = -1;
- }
-
- index() {
- const map = this.map;
- const array = this.array;
- const partialMap = Object.create(null);
-
- var k, kp;
- var i, len;
-
- // Create a map that will contain all keys and partial keys.
- for (k in map) {
- if (!k) {
- partialMap[k] = k;
- }
- else {
- for (i = 0, len = k.length; i < len; i++) {
- kp = k.substr(i);
- if (!hasOwn.call(partialMap, kp) || partialMap[kp].length < len)
- partialMap[kp] = k;
- }
- }
- }
-
- // Create an array that will only contain keys that are needed.
- for (k in map)
- if (partialMap[k] === k)
- array.push(k);
- array.sort();
-
- // Create valid offsets to the `array`.
- var offMap = Object.create(null);
- var offset = 0;
-
- for (i = 0, len = array.length; i < len; i++) {
- k = array[i];
-
- offMap[k] = offset;
- offset += k.length + 1;
- }
- this.size = offset;
-
- // Assign valid offsets to `map`.
- for (kp in map) {
- k = partialMap[kp];
- map[kp] = offMap[k] + k.length - kp.length;
- }
- }
-
- format(indent, justify) {
- if (this.size === -1)
- throw new Error(`IndexedString.format(): not indexed yet, call index()`);
-
- const array = this.array;
- if (!justify) justify = 0;
-
- var i;
- var s = "";
- var line = "";
-
- for (i = 0; i < array.length; i++) {
- const item = "\"" + array[i] + ((i !== array.length - 1) ? "\\0\"" : "\";");
- const newl = line + (line ? " " : indent) + item;
-
- if (newl.length <= justify) {
- line = newl;
- continue;
- }
- else {
- s += line + "\n";
- line = indent + item;
- }
- }
-
- return s + line;
- }
-
- getSize() {
- if (this.size === -1)
- throw new Error(`IndexedString.getSize(): Not indexed yet, call index()`);
- return this.size;
- }
-
- getIndex(k) {
- if (this.size === -1)
- throw new Error(`IndexedString.getIndex(): Not indexed yet, call index()`);
-
- if (!hasOwn.call(this.map, k))
- throw new Error(`IndexedString.getIndex(): Key '${k}' not found.`);
-
- return this.map[k];
- }
-}
+// Create the X86 database and add some special cases recognized by AsmJit.
+const x86 = base.asmdb.x86;
+const isa = new x86.ISA({
+ instructions: [
+ // Imul in [reg, imm] form is encoded as [reg, reg, imm].
+ ["imul" , "r16, ib" , "RM" , "66 6B /r ib" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
+ ["imul" , "r32, ib" , "RM" , "6B /r ib" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
+ ["imul" , "r64, ib" , "RM" , "REX.W 6B /r ib" , "X64 OF=W SF=W ZF=U AF=U PF=U CF=W"],
+ ["imul" , "r16, iw" , "RM" , "66 69 /r iw" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
+ ["imul" , "r32, id" , "RM" , "69 /r id" , "ANY OF=W SF=W ZF=U AF=U PF=U CF=W"],
+ ["imul" , "r64, id" , "RM" , "REX.W 69 /r id" , "X64 OF=W SF=W ZF=U AF=U PF=U CF=W"]
+ ]
+});
+
+// var fs = require("fs");
+// fs.writeFileSync("X86.JSON", JSON.stringify(isa.instructionMap, null, 2));
// ----------------------------------------------------------------------------
// [GenUtils]
// ----------------------------------------------------------------------------
+const RemappedInsts = {
+ __proto__: null,
+
+ "cmpsd": { names: ["cmpsd"] , rep: false },
+ "movsd": { names: ["movsd"] , rep: false },
+ "cmps" : { names: ["cmpsb", "cmpsw", "cmpsd", "cmpsq"], rep: true },
+ "movs" : { names: ["movsb", "movsw", "movsd", "movsq"], rep: true },
+ "lods" : { names: ["lodsb", "lodsw", "lodsd", "lodsq"], rep: null },
+ "scas" : { names: ["scasb", "scasw", "scasd", "scasq"], rep: null },
+ "stos" : { names: ["stosb", "stosw", "stosd", "stosq"], rep: null },
+ "ins" : { names: ["insb" , "insw" , "insd" ] , rep: null },
+ "outs" : { names: ["outsb", "outsw", "outsd"] , rep: null }
+};
+
class GenUtils {
// Get group of instructions having the same name as understood by AsmJit.
static groupOf(name) {
- var rep = null;
- var names = null;
-
- switch (name) {
- // Remap / filter these instructions.
- case "cmpsd": names = ["cmpsd"]; rep = false; break;
- case "movsd": names = ["movsd"]; rep = false; break;
- case "cmps" : names = ["cmpsb", "cmpsw", "cmpsd", "cmpsq"]; rep = true; break;
- case "movs" : names = ["movsb", "movsw", "movsd", "movsq"]; rep = true; break;
- case "lods" : names = ["lodsb", "lodsw", "lodsd", "lodsq"]; break;
- case "scas" : names = ["scasb", "scasw", "scasd", "scasq"]; break;
- case "stos" : names = ["stosb", "stosw", "stosd", "stosq"]; break;
- case "ins" : names = ["insb" , "insw" , "insd" ]; break;
- case "outs" : names = ["outsb", "outsw", "outsd"]; break;
+ const remapped = RemappedInsts[name];
+ if (!remapped) return isa.query(name);
- default:
- return x86db.getGroup(name);
- }
+ const insts = isa.query(remapped.names);
+ const rep = remapped.rep;
+ if (rep === null) return insts;
- const insts = [];
- for (var i = 0; i < names.length; i++) {
- insts.push.apply(insts, x86db.getGroup(names[i]));
- }
+ return insts.filter(function(inst) {
+ return rep === !!(inst.attributes.REP || inst.attributes.REPZ || inst.attributes.REPNZ);
+ });
+ }
- if (rep === null)
- return insts;
+ static archOf(group) {
+ var anyArch = false;
+ var x86Arch = false;
+ var x64Arch = false;
- // Filter, if needed.
- const output = [];
- for (var i = 0; i < insts.length; i++) {
- const inst = insts[i];
- if (rep === !!(inst.rep || inst.repz || inst.repnz))
- output.push(inst);
+ for (var i = 0; i < group.length; i++) {
+ const inst = group[i];
+ if (inst.arch === "ANY") anyArch = true;
+ if (inst.arch === "X86") x86Arch = true;
+ if (inst.arch === "X64") x64Arch = true;
}
- return output;
+
+ return anyArch || (x86Arch && x64Arch) ? "[ANY]" : x86Arch ? "[X86]" : "[X64]";
}
// Calculate a family of a group of instructions.
- static familyOf(insts) {
+ static familyOf(group) {
var i, j;
var nSSE = 0;
var nAVX = 0;
-
- for (i = 0; i < insts.length; i++) {
- const inst = insts[i];
+
+ for (i = 0; i < group.length; i++) {
+ const inst = group[i];
const ops = inst.operands;
if (/^(VEX|XOP|EVEX)$/.test(inst.prefix)) {
@@ -322,24 +114,24 @@ class GenUtils {
}
}
- if (nSSE === insts.length) return "Sse";
- if (nAVX === insts.length) return "Avx";
-
+ if (nSSE === group.length) return "Sse";
+ if (nAVX === group.length) return "Avx";
+
return "General";
}
- static featuresOf(insts) {
+ static featuresOf(group) {
const features = Object.create(null);
- for (var i = 0; i < insts.length; i++)
- for (var feature in insts[i].cpu)
+ for (var i = 0; i < group.length; i++)
+ for (var feature in group[i].extensions)
features[feature] = true;
const result = Object.getOwnPropertyNames(features);
result.sort();
return result;
}
-
+
static eqOps(aOps, aFrom, bOps, bFrom) {
var x = 0;
for (;;) {
@@ -361,7 +153,92 @@ class GenUtils {
x++;
}
}
-};
+
+ static singleRegCase(name) {
+ switch (name) {
+ case "xchg" :
+
+ case "and" :
+ case "pand" : case "vpand" : case "vpandd" : case "vpandq" :
+ case "andpd" : case "vandpd" :
+ case "andps" : case "vandps" :
+
+ case "or" :
+ case "por" : case "vpor" : case "vpord" : case "vporq" :
+ case "orpd" : case "vorpd" :
+ case "orps" : case "vorps" :
+
+ case "pminsb" : case "vpminsb" : case "pmaxsb" : case "vpmaxsb" :
+ case "pminsw" : case "vpminsw" : case "pmaxsw" : case "vpmaxsw" :
+ case "pminsd" : case "vpminsd" : case "pmaxsd" : case "vpmaxsd" :
+ case "pminub" : case "vpminub" : case "pmaxub" : case "vpmaxub" :
+ case "pminuw" : case "vpminuw" : case "pmaxuw" : case "vpmaxuw" :
+ case "pminud" : case "vpminud" : case "pmaxud" : case "vpmaxud" :
+ return "RO";
+
+ case "pandn" : case "vpandn" : case "vpandnd" : case "vpandnq" :
+
+ case "xor" :
+ case "pxor" : case "vpxor" : case "vpxord" : case "vpxorq" :
+ case "xorpd" : case "vxorpd" :
+ case "xorps" : case "vxorps" :
+
+ case "sub" :
+ case "psubb" : case "vpsubb" :
+ case "psubw" : case "vpsubw" :
+ case "psubd" : case "vpsubd" :
+ case "psubq" : case "vpsubq" :
+ case "psubsb" : case "vpsubsb" : case "psubusb" : case "vpsubusb" :
+ case "psubsw" : case "vpsubsw" : case "psubusw" : case "vpsubusw" :
+
+ case "vpcmpeqb": case "pcmpeqb" : case "vpcmpgtb": case "pcmpgtb" :
+ case "vpcmpeqw": case "pcmpeqw" : case "vpcmpgtw": case "pcmpgtw" :
+ case "vpcmpeqd": case "pcmpeqd" : case "vpcmpgtd": case "pcmpgtd" :
+ case "vpcmpeqq": case "pcmpeqq" : case "vpcmpgtq": case "pcmpgtq" :
+
+ case "vpcmpb" : case "vpcmpub" :
+ case "vpcmpd" : case "vpcmpud" :
+ case "vpcmpw" : case "vpcmpuw" :
+ case "vpcmpq" : case "vpcmpuq" :
+ return "WO";
+
+ default:
+ return "None";
+ }
+ }
+
+ static jumpType(name) {
+ switch (name) {
+ case "jo" :
+ case "jno":
+ case "jb" : case "jnae":
+ case "jae": case "jnb" :
+ case "je" : case "jz" :
+ case "jne": case "jnz" :
+ case "jbe": case "jna" :
+ case "js" :
+ case "jns":
+ case "jp" : case "jpe" :
+ case "jnp": case "jpo" :
+ case "jl" : case "jnge":
+ case "jge": case "jnl" :
+ case "jle": case "jng" :
+ case "jg" : case "jnle":
+ case "jecxz":
+ case "loop":
+ case "loope":
+ case "loopne":
+ return "Conditional";
+
+ case "jmp" : return "Direct";
+ case "call": return "Call";
+ case "ret" : return "Return";
+
+ default:
+ return "None";
+ }
+ }
+}
// ----------------------------------------------------------------------------
// [Generate]
@@ -458,8 +335,8 @@ const OpToAsmJitOp = {
"xmm" : "FLAG(Xmm)",
"ymm" : "FLAG(Ymm)",
"zmm" : "FLAG(Zmm)",
- "sreg" : "FLAG(Seg)",
"bnd" : "FLAG(Bnd)",
+ "sreg" : "FLAG(Seg)",
"creg" : "FLAG(Cr)",
"dreg" : "FLAG(Dr)",
@@ -554,8 +431,8 @@ class OSignature {
var hasReg = false;
for (k in af) {
- const index = asmdb.x86util.misc.regIndexOf(k);
- const kind = asmdb.x86util.misc.regKindOf(k);
+ const index = x86.Utils.regIndexOf(k);
+ const kind = x86.Utils.regKindOf(k);
if (kind)
hasReg = true;
@@ -566,9 +443,9 @@ class OSignature {
if (hasReg) {
for (k in bf) {
- const index = asmdb.x86util.misc.regIndexOf(k);
+ const index = x86.Utils.regIndexOf(k);
if (index !== null && index !== -1) {
- const kind = asmdb.x86util.misc.regKindOf(k);
+ const kind = x86.Utils.regKindOf(k);
if (indexKind !== kind) return false;
}
}
@@ -628,7 +505,6 @@ class OSignature {
}
toAsmJitOpData() {
- var s = "";
var oFlags = this.flags;
var mFlags = Object.create(null);
@@ -751,7 +627,7 @@ class OSignature {
const sMemFlags = StringifyArray(SortOpArray(Object.getOwnPropertyNames(mMemFlags)), OpToAsmJitOp);
const sExtFlags = StringifyArray(SortOpArray(Object.getOwnPropertyNames(mExtFlags)), OpToAsmJitOp);
- return `OSIGNATURE(${sFlags || 0}, ${sMemFlags || 0}, ${sExtFlags || 0}, ${Utils.decToHex(sRegMask, 2)})`;
+ return `OSIGNATURE(${sFlags || 0}, ${sMemFlags || 0}, ${sExtFlags || 0}, ${StringUtils.decToHex(sRegMask, 2)})`;
}
}
@@ -807,7 +683,7 @@ class ISignature extends Array {
return false;
}
- // Bail if mergeWidth and operand-level failed.
+ // Bail if mergeWidth at operand-level failed.
if (xorIndex !== -1 && !this[xorIndex].mergeWith(other[xorIndex]))
return false;
@@ -817,7 +693,7 @@ class ISignature extends Array {
return true;
}
- toString(ops) {
+ toString() {
return "{" + this.join(", ") + "}";
}
}
@@ -842,7 +718,7 @@ class SignatureArray extends Array {
this[i].simplify();
}
- toString(ops) {
+ toString() {
return "[" + this.join(", ") + "]";
}
}
@@ -851,10 +727,9 @@ class SignatureArray extends Array {
// [X86Generator]
// ----------------------------------------------------------------------------
-class X86Generator {
+class X86Generator extends base.BaseGenerator {
constructor() {
- this.instMap = Object.create(null);
- this.instArray = [];
+ super("X86");
this.opCombinations = Object.create(null);
this.maxOpRows = 0;
@@ -866,7 +741,10 @@ class X86Generator {
"moff64": true
};
- this.sizeStats = Object.create(null);
+ this.load([
+ "src/asmjit/x86/x86inst.cpp",
+ "src/asmjit/x86/x86inst.h"
+ ]);
}
signaturesFromInsts(insts) {
@@ -955,165 +833,97 @@ class X86Generator {
// [Parse]
// --------------------------------------------------------------------------
- parse(data) {
- // Create database.
+ parse() {
+ const data = this.dataOf("src/asmjit/x86/x86inst.cpp");
const re = new RegExp(
- "INST\\(([A-Za-z0-9_]+)\\s*," + // [01] Id.
- "\\s*\\\"([A-Za-z0-9_ ]*)\\\"\\s*," + // [02] Name.
- "([^,]+)," + // [03] Encoding.
- "(.{26}[^,]*)," + // [04] Opcode[0].
- "(.{26}[^,]*)," + // [05] Opcode[1].
- "(.{38}[^,]*)," + // [06] IFLAGS.
- "\\s*EF\\(([A-Z_]+)\\)\\s*," + // [07] EFLAGS.
- "([^,]+)," + // [08] Write-Index.
- "([^,]+)," + // [09] Write-Size.
- // --- autogenerated ---
- "([^\\)]+)," + // [10] FamilyType.
- "([^\\)]+)," + // [11] FamilyIndex.
- "([^\\)]+)," + // [12] NameIndex.
- "([^\\)]+)\\)", // [13] ExtIndex.
+ "INST\\(" +
+ "([A-Za-z0-9_]+)\\s*" + "," + // [01] Instruction.
+ "([^,]+)" + "," + // [02] Encoding.
+ "(.{26}[^,]*)" + "," + // [03] Opcode[0].
+ "(.{26}[^,]*)" + "," + // [04] Opcode[1].
+ "(.{38}[^,]*)" + "," + // [05] IFLAGS.
+ "\\s*EF\\(([A-Z_]+)\\)\\s*" + "," + // [06] EFLAGS.
+ "([^,]+)" + "," + // [07] Write-Index.
+ "([^,]+)" + "," + // [08] Write-Size.
+ // --- autogenerated fields ---
+ "([^\\)]+)" + "," + // [09] FamilyType.
+ "([^\\)]+)" + "," + // [10] FamilyIndex.
+ "([^\\)]+)" + "," + // [11] NameIndex.
+ "([^\\)]+)" + "\\)",// [12] ExtIndex.
"g");
- var id = 0;
var m;
-
- while (m = re.exec(data)) {
- var enum_ = kX86InstPrefix + m[1];
- var name = m[2];
- var encoding = m[3].trim();
- var opcode0 = m[4].trim();
- var opcode1 = m[5].trim();
- var iflags = m[6].trim();
- var eflags = m[7];
- var writeIndex = Utils.trimLeft(m[8]);
- var writeSize = Utils.trimLeft(m[9]);
+ while ((m = re.exec(data)) !== null) {
+ var enum_ = m[1];
+ var name = enum_ === "None" ? "" : enum_.toLowerCase();
+ var encoding = m[2].trim();
+ var opcode0 = m[3].trim();
+ var opcode1 = m[4].trim();
+ var iflags = m[5].trim();
+ var eflags = m[6];
+ var writeIndex = StringUtils.trimLeft(m[7]);
+ var writeSize = StringUtils.trimLeft(m[8]);
const insts = GenUtils.groupOf(name);
- if (!insts)
+ if (!insts.length)
console.log(`INSTRUCTION '${name}' not found in asmdb`);
- const signatures = insts ? this.signaturesFromInsts(insts) : new SignatureArray();
- const inst = {
- id : id, // Instruction id.
- name : name, // Instruction name.
- enum : enum_, // Instruction enum-string (kX86InstId...).
- encoding : encoding, // Instruction encoding.
- opcode0 : opcode0, // Primary opcode.
- opcode1 : opcode1, // Secondary opcode.
+ const signatures = this.signaturesFromInsts(insts);
+ const singleRegCase = GenUtils.singleRegCase(name);
+ const jumpType = GenUtils.jumpType(name);
+
+ this.addInst({
+ id : 0, // Instruction id (numeric value).
+ name : name, // Instruction name.
+ enum : enum_, // Instruction enum without `kId` prefix.
+ encoding : encoding, // Instruction encoding.
+ opcode0 : opcode0, // Primary opcode.
+ opcode1 : opcode1, // Secondary opcode.
iflags : iflags,
eflags : eflags,
writeIndex : writeIndex,
writeSize : writeSize,
- signatures : signatures, // Rows containing instruction signatures.
+ signatures : signatures, // Rows containing instruction signatures.
+ singleRegCase : singleRegCase,
+ jumpType : jumpType,
- familyType : "kFamilyNone",// Family type.
- familyIndex : 0, // Index to a family-specific data.
+ familyType : "kFamilyNone", // Family type.
+ familyIndex : 0, // Index to a family-specific data.
- nameIndex : -1, // Instruction name-index.
- altOpCodeIndex: -1, // Index to X86InstDB::altOpCodeTable.
+ nameIndex : -1, // Instruction name-index.
+ altOpCodeIndex: -1, // Index to X86InstDB::altOpCodeTable.
commonIndex : -1,
signatureIndex: -1,
signatureCount: -1
- }
-
- this.instMap[name] = inst;
- this.instArray.push(inst);
+ });
this.maxOpRows = Math.max(this.maxOpRows, signatures.length);
-
- id++;
}
+ if (this.instArray.length === 0)
+ throw new Error("X86Generator.parse(): Invalid parsing regexp (no data parsed)");
+
console.log("Number of Instructions: " + this.instArray.length);
}
// --------------------------------------------------------------------------
- // [Generate - All]
+ // [Generate]
// --------------------------------------------------------------------------
- generate(oldData) {
- var data = oldData;
-
- function myInject(key, str) {
- data = Utils.inject(data,
- "// ${" + key + ":Begin}\n",
- "// ${" + key + ":End}\n", str);
- }
-
+ generate() {
// Order doesn't matter here.
- myInject("nameData" , this.generateNameData());
- myInject("fpuData" , this.generateFpuData());
- myInject("sseData" , this.generateSseData());
- myInject("avxData" , this.generateAvxData());
- myInject("altOpCodeData" , this.generateAltOpCodeData());
- myInject("signatureData" , this.generateSignatureData());
- // These must be last.
- myInject("commonData" , this.generateCommonData());
- myInject("instData" , this.generateInstData());
-
- return data;
- }
-
- // --------------------------------------------------------------------------
- // [Generate - NameData]
- // --------------------------------------------------------------------------
-
- generateNameData() {
- const instArray = this.instArray;
-
- const instNames = new IndexedString();
- const instAlpha = new Array(26);
-
- var maxLength = 0;
-
- for (var i = 0; i < instArray.length; i++) {
- const inst = instArray[i];
- instNames.add(inst.name);
- maxLength = Math.max(maxLength, inst.name.length);
- }
- instNames.index();
-
- for (var i = 0; i < instArray.length; i++) {
- const inst = instArray[i];
- const name = inst.name;
- const nameIndex = instNames.getIndex(name);
-
- const aIndex = name.charCodeAt(0) - 'a'.charCodeAt(0);
- if (aIndex < 0 || aIndex >= 26)
- throw new Error("Alphabetical index error");
-
- inst.nameIndex = nameIndex;
- if (instAlpha[aIndex] === undefined)
- instAlpha[aIndex] = inst.enum;
- }
-
- var s = "";
- s += kDisclaimerStart;
- s += `const char X86InstDB::nameData[] =\n${instNames.format(kIndent, kJustify)}\n`;
- s += `\n`;
- s += `enum {\n`;
- s += ` kX86InstMaxLength = ${maxLength}\n`;
- s += `};\n`;
- s += `\n`;
- s += `enum X86InstAlphaIndex {\n`;
- s += ` kX86InstAlphaIndexFirst = 'a',\n`;
- s += ` kX86InstAlphaIndexLast = 'z',\n`;
- s += ` kX86InstAlphaIndexInvalid = 0xFFFF\n`;
- s += `};\n`;
- s += `\n`;
-
- s += `static const uint16_t _x86InstAlphaIndex[26] = {\n`;
- for (var i = 0; i < instAlpha.length; i++) {
- const id = instAlpha[i];
- s += kIndent + (id === undefined ? "0xFFFF" : id);
- if (i !== instAlpha.length - 1)
- s += `,`;
- s += `\n`;
- }
- s += `};\n`;
- s += kDisclaimerEnd;
-
- this.sizeStats.NameData = instNames.getSize() + instAlpha.length * 2;
- return s;
+ this.generateIdData();
+ this.generateNameData();
+ this.generateFpuData();
+ this.generateSseData();
+ this.generateAvxData();
+ this.generateAltOpCodeData();
+ this.generateSignatureData();
+
+ // These must be last, and order matters.
+ this.generateCommonData();
+ this.generateInstData();
+
+ return this;
}
// --------------------------------------------------------------------------
@@ -1121,16 +931,14 @@ class X86Generator {
// --------------------------------------------------------------------------
generateAltOpCodeData() {
- const table = new IndexedArray();
+ const table = new base.IndexedArray();
for (var i = 0; i < this.instArray.length; i++) {
const inst = this.instArray[i];
- inst.altOpCodeIndex = table.addIndexed(Utils.padLeft(inst.opcode1, 26));
+ inst.altOpCodeIndex = table.addIndexed(StringUtils.padLeft(inst.opcode1, 26));
}
- this.sizeStats.AltOpCodeData = table.length * 4;
- return kDisclaimerStart +
- `const uint32_t X86InstDB::altOpCodeData[] = {\n${Utils.format(table, kIndent, true)}\n};\n` +
- kDisclaimerEnd;
+ var s = `const uint32_t X86InstDB::altOpCodeData[] = {\n${StringUtils.format(table, kIndent, true)}\n};\n`;
+ return this.inject("altOpCodeData", StringUtils.disclaimer(s), table.length * 4);
}
// --------------------------------------------------------------------------
@@ -1138,7 +946,7 @@ class X86Generator {
// --------------------------------------------------------------------------
generateFpuData() {
- return "";
+ return this;
}
// --------------------------------------------------------------------------
@@ -1150,7 +958,7 @@ class X86Generator {
const instMap = this.instMap;
const prefix = "X86Inst::SseData::";
- const table = new IndexedArray();
+ const table = new base.IndexedArray();
function getSseToAvxInsts(insts) {
const combinations = [];
@@ -1188,7 +996,7 @@ class X86Generator {
const avxName = "v" + sseName;
const avxInsts = GenUtils.groupOf(avxName);
- if (!avxInsts) {
+ if (!avxInsts.length) {
console.log(`SseToAvx: Instruction '${sseName}' has no AVX counterpart`);
return null;
}
@@ -1229,7 +1037,7 @@ class X86Generator {
}
out.avxConvMode = (map.raw && !map.nds) ? "Move" :
- (map.raw && map.nds) ? "MoveIfMem" : "NonDestructive";
+ (map.raw && map.nds) ? "MoveIfMem" : "Extend";
}
out.avxConvDelta = instMap[avxName].id - instMap[sseName].id;
}
@@ -1237,7 +1045,9 @@ class X86Generator {
for (var i = 0; i < instArray.length; i++) {
const inst = instArray[i];
const insts = GenUtils.groupOf(inst.name);
- if (!insts) continue;
+
+ if (!insts.length)
+ continue;
if (GenUtils.familyOf(insts) === "Sse") {
const data = {
@@ -1246,26 +1056,24 @@ class X86Generator {
};
calcSseToAvxData(insts, data);
- var features = GenUtils.featuresOf(insts).map(function(f) { return Utils.padLeft(`FEATURE(${f})`, 19); }).join(`|\n${kIndent} `);
- if (!features) features = Utils.padLeft("0", 19);
-
+ var features = GenUtils.featuresOf(insts).map(function(f) { return StringUtils.padLeft(`FEATURE(${f})`, 19); }).join(`|\n${kIndent} `);
+ if (!features) features = StringUtils.padLeft("0", 19);
+
inst.familyType = "kFamilySse";
inst.familyIndex = table.addIndexed(
"{ " + features + ", " +
- Utils.padLeft(`CONV_MODE(${data.avxConvMode})`, 26) + ", " +
- Utils.padLeft(data.avxConvDelta , 4) + " }"
+ StringUtils.padLeft(`AVX_CONV(${data.avxConvMode})`, 20) + ", " +
+ StringUtils.padLeft(data.avxConvDelta , 4) + " }"
);
}
}
- this.sizeStats.SseData = table.length * 4;
-
- return kDisclaimerStart +
- `#define FEATURE(F) ${prefix}kFeature##F\n` +
- `#define CONV_MODE(MODE) ${prefix}kAvxConv##MODE\n` +
- `const X86Inst::SseData X86InstDB::sseData[] = {\n${Utils.format(table, kIndent, true)}\n};\n` +
- `#undef CONV_MODE\n` +
- `#undef FEATURE\n` +
- kDisclaimerEnd;
+
+ var s = `#define FEATURE(F) ${prefix}kFeature##F\n` +
+ `#define AVX_CONV(MODE) ${prefix}kAvxConv##MODE\n` +
+ `const X86Inst::SseData X86InstDB::sseData[] = {\n${StringUtils.format(table, kIndent, true)}\n};\n` +
+ `#undef AVX_CONV\n` +
+ `#undef FEATURE\n`;
+ return this.inject("sseData", StringUtils.disclaimer(s), table.length * 4);
}
// --------------------------------------------------------------------------
@@ -1276,13 +1084,9 @@ class X86Generator {
const instArray = this.instArray;
const prefix = "X86Inst::AvxData::";
- const table = new IndexedArray();
+ const table = new base.IndexedArray();
function fillFlags(insts, out) {
- var broadcast = "0";
- var masking = "0";
- var er_sae = "0"
-
for (var i = 0; i < insts.length; i++) {
const inst = insts[i];
if (inst.prefix === "EVEX") {
@@ -1298,11 +1102,13 @@ class X86Generator {
for (var i = 0; i < instArray.length; i++) {
const inst = instArray[i];
const insts = GenUtils.groupOf(inst.name);
- if (!insts) continue;
+
+ if (!insts.length)
+ continue;
if (GenUtils.familyOf(insts) === "Avx") {
- var features = GenUtils.featuresOf(insts).map(function(f) { return Utils.padLeft(`FEATURE(${f})`, 19); }).join(`|\n${kIndent} `);
- if (!features) features = Utils.padLeft("0", 19);
+ var features = GenUtils.featuresOf(insts).map(function(f) { return StringUtils.padLeft(`FEATURE(${f})`, 19); }).join(`|\n${kIndent} `);
+ if (!features) features = StringUtils.padLeft("0", 19);
const flagsMap = {};
fillFlags(insts, flagsMap);
@@ -1317,16 +1123,13 @@ class X86Generator {
inst.familyIndex = table.addIndexed("{ " + features + ", " + flags + " }");
}
}
- this.sizeStats.AvxData = table.length * 8;
-
- return kDisclaimerStart +
- `#define FEATURE(F) ${prefix}kFeature##F\n` +
- `#define FLAG(F) ${prefix}kFlag##F\n` +
- `const X86Inst::AvxData X86InstDB::avxData[] = {\n${Utils.format(table, kIndent, true)}\n};\n` +
- `#undef FLAG\n` +
- `#undef FEATURE\n` +
- kDisclaimerEnd;
- return "";
+
+ var s = `#define FEATURE(F) ${prefix}kFeature##F\n` +
+ `#define FLAG(F) ${prefix}kFlag##F\n` +
+ `const X86Inst::AvxData X86InstDB::avxData[] = {\n${StringUtils.format(table, kIndent, true)}\n};\n` +
+ `#undef FLAG\n` +
+ `#undef FEATURE\n`;
+ return this.inject("avxData", StringUtils.disclaimer(s), table.length * 8);
}
// --------------------------------------------------------------------------
@@ -1346,21 +1149,6 @@ class X86Generator {
opMap[noOperand] = [0];
opArr.push(noOperand);
- function makeCxxArray(array, code) {
- return `${code} = {\n` +
- kIndent + array.join(`,\n${kIndent}`) + "\n" +
- `};\n`;
- }
-
- function makeCxxArrayWithComment(array, code) {
- var s = "";
- for (var i = 0; i < array.length; i++) {
- const last = i === array.length - 1;
- s += kIndent + array[i].data + (last ? " // " : ", // ") + Utils.padLeft(array[i].refs ? "#" + String(i) : "", 5) + array[i].comment + "\n";
- }
- return `${code} = {\n${s}};\n`;
- }
-
function findSignaturesIndex(rows) {
const len = rows.length;
if (!len) return 0;
@@ -1430,12 +1218,12 @@ class X86Generator {
index = opMap[h];
}
- signatureEntry += `, ${Utils.padLeft(index, 3)}`;
+ signatureEntry += `, ${StringUtils.padLeft(index, 3)}`;
x++;
}
while (x < 6) {
- signatureEntry += `, ${Utils.padLeft(0, 3)}`;
+ signatureEntry += `, ${StringUtils.padLeft(0, 3)}`;
x++;
}
@@ -1455,31 +1243,25 @@ class X86Generator {
}
}
- var s = "";
-
- s += kDisclaimerStart;
- s += "#define ISIGNATURE(count, x86, x64, implicit, o0, o1, o2, o3, o4, o5) \\\n";
- s += " { count, (x86 ? uint8_t(X86Inst::kArchMaskX86) : uint8_t(0)) | \\\n";
- s += " (x64 ? uint8_t(X86Inst::kArchMaskX64) : uint8_t(0)) , \\\n";
- s += " implicit, \\\n";
- s += " 0, \\\n";
- s += " o0, o1, o2, o3, o4, o5 \\\n";
- s += " }\n";
- s += makeCxxArrayWithComment(signatureArr, "static const X86Inst::ISignature _x86InstISignatureData[]");
- s += "#undef ISIGNATURE\n";
- s += "\n";
- s += "#define FLAG(flag) X86Inst::kOp##flag\n";
- s += "#define MEM(mem) X86Inst::kMemOp##mem\n";
- s += "#define OSIGNATURE(flags, memFlags, extFlags, regId) \\\n";
- s += " { uint32_t(flags), uint16_t(memFlags), uint8_t(extFlags), uint8_t(regId) }\n";
- s += makeCxxArray(opArr, "static const X86Inst::OSignature _x86InstOSignatureData[]");
- s += "#undef OSIGNATURE\n";
- s += "#undef MEM\n";
- s += "#undef FLAG\n";
- s += kDisclaimerEnd;
-
- this.sizeStats.SignatureData = opArr.length * 8 + signatureArr.length * 8;
- return s;
+ var s = "#define ISIGNATURE(count, x86, x64, implicit, o0, o1, o2, o3, o4, o5) \\\n" +
+ " { count, (x86 ? uint8_t(X86Inst::kArchMaskX86) : uint8_t(0)) | \\\n" +
+ " (x64 ? uint8_t(X86Inst::kArchMaskX64) : uint8_t(0)) , \\\n" +
+ " implicit, \\\n" +
+ " 0, \\\n" +
+ " { o0, o1, o2, o3, o4, o5 } \\\n" +
+ " }\n" +
+ StringUtils.makeCxxArrayWithComment(signatureArr, "static const X86Inst::ISignature _x86InstISignatureData[]") +
+ "#undef ISIGNATURE\n" +
+ "\n" +
+ "#define FLAG(flag) X86Inst::kOp##flag\n" +
+ "#define MEM(mem) X86Inst::kMemOp##mem\n" +
+ "#define OSIGNATURE(flags, memFlags, extFlags, regId) \\\n" +
+ " { uint32_t(flags), uint16_t(memFlags), uint8_t(extFlags), uint8_t(regId) }\n" +
+ StringUtils.makeCxxArray(opArr, "static const X86Inst::OSignature _x86InstOSignatureData[]") +
+ "#undef OSIGNATURE\n" +
+ "#undef MEM\n" +
+ "#undef FLAG\n";
+ return this.inject("signatureData", StringUtils.disclaimer(s), opArr.length * 8 + signatureArr.length * 8);
}
// --------------------------------------------------------------------------
@@ -1487,28 +1269,34 @@ class X86Generator {
// --------------------------------------------------------------------------
generateCommonData() {
- const table = new IndexedArray();
+ const table = new base.IndexedArray();
for (var i = 0; i < this.instArray.length; i++) {
const inst = this.instArray[i];
- const eflagsIn = Utils.decToHex(getEFlagsMask(inst.eflags, "RX" ), 2);
- const eflagsOut = Utils.decToHex(getEFlagsMask(inst.eflags, "WXU"), 2);
-
- const item = "{ " + Utils.padLeft(inst.iflags , 38) + ", " +
- Utils.padLeft(inst.writeIndex , 3) + ", " +
- Utils.padLeft(inst.writeSize , 3) + ", " +
- eflagsIn + ", " +
- eflagsOut + ", " +
- Utils.padLeft(inst.altOpCodeIndex, 3) + ", " +
- Utils.padLeft(inst.signatureIndex, 3) + ", " +
- Utils.padLeft(inst.signatureCount, 2) + ", 0 }";
+ const eflagsIn = StringUtils.decToHex(getEFlagsMask(inst.eflags, "RX" ), 2);
+ const eflagsOut = StringUtils.decToHex(getEFlagsMask(inst.eflags, "WXU"), 2);
+ const singleRegCase = `SINGLE_REG(${inst.singleRegCase})`;
+ const jumpType = `JUMP_TYPE(${inst.jumpType})`;
+
+ const item = "{ " + StringUtils.padLeft(inst.iflags , 38) + ", " +
+ StringUtils.padLeft(inst.writeIndex , 3) + ", " +
+ StringUtils.padLeft(inst.writeSize , 3) + ", " +
+ eflagsIn + ", " +
+ eflagsOut + ", " +
+ StringUtils.padLeft(inst.altOpCodeIndex, 3) + ", " +
+ StringUtils.padLeft(inst.signatureIndex, 3) + ", " +
+ StringUtils.padLeft(inst.signatureCount, 2) + ", " +
+ StringUtils.padLeft(jumpType , 22) + ", " +
+ StringUtils.padLeft(singleRegCase , 16) + ", " + "0 }";
inst.commonIndex = table.addIndexed(item);
}
- this.sizeStats.CommonData = table.length * 12;
- return kDisclaimerStart +
- `const X86Inst::CommonData X86InstDB::commonData[] = {\n${Utils.format(table, kIndent, true)}\n};\n` +
- kDisclaimerEnd;
+ var s = `#define JUMP_TYPE(VAL) AnyInst::kJumpType##VAL\n` +
+ `#define SINGLE_REG(VAL) X86Inst::kSingleReg##VAL\n` +
+ `const X86Inst::CommonData X86InstDB::commonData[] = {\n${StringUtils.format(table, kIndent, true)}\n};\n` +
+ `#undef SINGLE_REG\n` +
+ `#undef JUMP_TYPE\n`;
+ return this.inject("commonData", StringUtils.disclaimer(s), table.length * 12);
}
// --------------------------------------------------------------------------
@@ -1516,24 +1304,47 @@ class X86Generator {
// --------------------------------------------------------------------------
generateInstData() {
- this.sizeStats.InstData = this.instArray.length * 12;
-
- return Utils.format(this.instArray, kIndent, false, function(inst) {
+ var s = StringUtils.format(this.instArray, "", false, function(inst) {
return "INST(" +
- Utils.padLeft(inst.enum.substr(kX86InstPrefix.length), 16) + ", " +
- Utils.padLeft(`"${inst.name}"` , 18) + ", " +
- Utils.padLeft(inst.encoding , 23) + ", " +
- Utils.padLeft(inst.opcode0 , 26) + ", " +
- Utils.padLeft(inst.opcode1 , 26) + ", " +
- Utils.padLeft(inst.iflags , 38) + ", " +
+ StringUtils.padLeft(inst.enum , 16) + ", " +
+ StringUtils.padLeft(inst.encoding , 19) + ", " +
+ StringUtils.padLeft(inst.opcode0 , 26) + ", " +
+ StringUtils.padLeft(inst.opcode1 , 26) + ", " +
+ StringUtils.padLeft(inst.iflags , 38) + ", " +
"EF(" + inst.eflags + "), " +
- Utils.padLeft(inst.writeIndex , 1) + ", " +
- Utils.padLeft(inst.writeSize , 1) + ", " +
- Utils.padLeft(inst.familyType , 11) + ", " +
- Utils.padLeft(inst.familyIndex , 3) + ", " +
- Utils.padLeft(inst.nameIndex , 4) + ", " +
- Utils.padLeft(inst.commonIndex , 3) + ")";
- }) + "\n ";
+ StringUtils.padLeft(inst.writeIndex , 1) + ", " +
+ StringUtils.padLeft(inst.writeSize , 1) + ", " +
+ StringUtils.padLeft(inst.familyType , 11) + ", " +
+ StringUtils.padLeft(inst.familyIndex, 3) + ", " +
+ StringUtils.padLeft(inst.nameIndex , 4) + ", " +
+ StringUtils.padLeft(inst.commonIndex, 3) + ")";
+ }) + "\n";
+ return this.inject("instData", s, this.instArray.length * 12);
+ }
+
+ // --------------------------------------------------------------------------
+ // [Reimplement]
+ // --------------------------------------------------------------------------
+
+ getCommentOf(name) {
+ var insts = GenUtils.groupOf(name);
+ if (!insts.length) return "";
+
+ var features = GenUtils.featuresOf(insts);
+ var comment = GenUtils.archOf(insts);
+
+ if (features.length) {
+ comment += " {";
+
+ const vl = features.indexOf("AVX512_VL");
+ if (vl !== -1) features.splice(vl, 1);
+ comment += features.join("|");
+ if (vl !== -1) comment += " (VL)";
+
+ comment += "}";
+ }
+
+ return comment;
}
// --------------------------------------------------------------------------
@@ -1541,61 +1352,43 @@ class X86Generator {
// --------------------------------------------------------------------------
printMissing() {
- const instArray = this.instArray;
-
var out = "";
function CPUFlags(insts) {
var flags = {};
for (var i = 0; i < insts.length; i++) {
var inst = insts[i];
- for (var k in inst.cpu)
+ for (var k in inst.extensions)
flags[k] = true;
}
return Object.getOwnPropertyNames(flags).join("|");
}
- x86db.getInstructionNames().forEach(function(name) {
- var insts = x86db.getGroup(name);
+ isa.instructionNames.forEach(function(name) {
+ var insts = isa.query(name);
if (!this.instMap[name]) {
console.log(`MISSING INSTRUCTION '${name}'`);
var inst = this.newInstFromInsts(insts);
if (inst) {
out += " INST(" +
- Utils.padLeft(inst.enum.substr(kX86InstPrefix.length), 16) + ", " +
- Utils.padLeft(`"${inst.name}"` , 18) + ", " +
- Utils.padLeft(inst.encoding , 23) + ", " +
- Utils.padLeft(inst.opcode0 , 26) + ", " +
- Utils.padLeft(inst.opcode1 , 26) + ", " +
- Utils.padLeft(inst.iflags , 38) + ", " +
+ StringUtils.padLeft(inst.enum , 16) + ", " +
+ StringUtils.padLeft(inst.encoding , 23) + ", " +
+ StringUtils.padLeft(inst.opcode0 , 26) + ", " +
+ StringUtils.padLeft(inst.opcode1 , 26) + ", " +
+ StringUtils.padLeft(inst.iflags , 38) + ", " +
"EF(" + inst.eflags + "), " +
- Utils.padLeft(inst.writeIndex , 2) + ", " +
- Utils.padLeft(inst.writeSize , 2) + ", " +
- Utils.padLeft(inst.signatureIndex, 3) + ", " +
- Utils.padLeft(inst.signatureCount, 2) + ", " +
- Utils.padLeft("0", 3) + ", " +
- Utils.padLeft("0", 3) + ", " +
- Utils.padLeft("0", 3) + "),\n";
+ StringUtils.padLeft(inst.writeIndex , 2) + ", " +
+ StringUtils.padLeft(inst.writeSize , 2) + ", " +
+ StringUtils.padLeft(inst.signatureIndex, 3) + ", " +
+ StringUtils.padLeft(inst.signatureCount, 2) + ", " +
+ StringUtils.padLeft("0", 3) + ", " +
+ StringUtils.padLeft("0", 3) + ", " +
+ StringUtils.padLeft("0", 3) + "),\n";
}
}
}, this);
console.log(out);
}
-
- printStats() {
- const stats = this.sizeStats;
-
- var pad = 24;
- var total = 0;
-
- for (var k in stats) {
- const size = stats[k];
- total += size;
- console.log(Utils.padLeft('Size of ' + k, pad) + ": " + size);
- }
-
- console.log(Utils.padLeft('Size of all tables', pad) + ": " + total);
- }
}
// ----------------------------------------------------------------------------
@@ -1603,19 +1396,13 @@ class X86Generator {
// ----------------------------------------------------------------------------
function main() {
- var g = new X86Generator();
- var data = fs.readFileSync(kFileName, "utf8").replace(/\r\n/g, "\n");
-
- g.parse(data);
- // g.printMissing();
- var newData = g.generate(data);
- g.printStats();
-
- // Save only if modified.
- if (newData !== data) {
- fs.writeFileSync(kFileName + ".backup", data, "utf8");
- fs.writeFileSync(kFileName, newData, "utf8");
- }
+ const gen = new X86Generator();
+
+ gen.parse();
+ gen.generate();
+ // gen.printMissing();
+ gen.dumpTableSizes();
+ gen.save();
}
main();
@@ -1662,7 +1449,7 @@ main();
var id = this.instArray.length;
var name = inst.name;
- var enum_ = kX86InstPrefix + name[0].toUpperCase() + name.substr(1);
+ var enum_ = kX86InstId + name[0].toUpperCase() + name.substr(1);
var opcode = inst.opcode;
var rm = inst.rm;
@@ -1716,8 +1503,8 @@ main();
evexW = obj.evexW;
}
- var ppmm = Utils.padLeft(pp, 2).replace(/ /g, "0") +
- Utils.padLeft(mm, 4).replace(/ /g, "0") ;
+ var ppmm = StringUtils.padLeft(pp, 2).replace(/ /g, "0") +
+ StringUtils.padLeft(mm, 4).replace(/ /g, "0") ;
var composed = composeOpCode({
type : prefix === "VEX" || prefix === "EVEX" ? "V" : "O",
@@ -1742,7 +1529,7 @@ main();
id : id,
name : name,
enum : enum_,
- encoding : "Enc(?" + encoding + "?)",
+ encoding : encoding,
opcode0 : composed,
opcode1 : "0",
iflags : iflags.join(""),
@@ -1757,12 +1544,12 @@ main();
function genAPI() {
var asm = fs.readFileSync("../src/asmjit/x86/x86assembler.h", "utf8");
- var list = ["AVX512F", "AVX512DQ", "AVX512BW", "AVX512CD", "AVX512ER", "AVX512PF", "AVX512IFMA", "AVX512VBMI"];
+ var list = ["AVX512_F", "AVX512_DQ", "AVX512_BW", "AVX512_CD", "AVX512_ER", "AVX512_PF", "AVX512_IFMA", "AVX512_VBMI"];
function getAVX512Flag(inst) {
- for (var cpu in inst.cpu) {
+ for (var cpu in inst.extensions) {
if (list.indexOf(cpu) !== -1) {
- return inst.cpu["AVX512VL"] ? cpu + "-VL" : cpu;
+ return inst.extensions["AVX512_VL"] ? cpu + "-VL" : cpu;
}
}
return "";
@@ -1789,8 +1576,8 @@ main();
"xmm0": "XMM0"
}
- x86db.forEach(function(name, inst) {
- if (inst.cpu.AVX || inst.cpu.AVX2 || getAVX512Flag(inst)) {
+ isa.forEach(function(name, inst) {
+ if (inst.extensions.AVX || inst.extensions.AVX2 || getAVX512Flag(inst)) {
var operands = inst.operands;
var iops = [];
var hasImm = -1;
@@ -1823,10 +1610,10 @@ main();
else
flags = flags + (avx512Flags.length ? "{" + avx512Flags.join("|") + "}" : "");
}
- else if (inst.cpu.AVX2) {
+ else if (inst.extensions.AVX2) {
flags = "AVX2";
}
- else if (inst.cpu.AVX) {
+ else if (inst.extensions.AVX) {
flags = "AVX";
}
else {
@@ -1905,11 +1692,11 @@ main();
if (flags.length) {
if (!fstr) fstr = " ";
- fstr = Utils.padLeft(fstr, 5);
+ fstr = StringUtils.padLeft(fstr, 5);
fstr += flags.join(" ");
}
- line = Utils.padLeft(line, 72);
+ line = StringUtils.padLeft(line, 72);
line += "// " + fstr;
}
@@ -1922,12 +1709,12 @@ main();
function genOpcodeH() {
var asm = fs.readFileSync("../src/asmjit/x86/x86assembler.h", "utf8");
- var list = ["AVX512F", "AVX512DQ", "AVX512BW", "AVX512CD", "AVX512ER", "AVX512PF", "AVX512IFMA", "AVX512VBMI"];
+ var list = ["AVX512_F", "AVX512_DQ", "AVX512_BW", "AVX512_CD", "AVX512_ER", "AVX512_PF", "AVX512_IFMA", "AVX512_VBMI"];
function getAVX512Flag(inst) {
- for (var cpu in inst.cpu) {
+ for (var cpu in inst.extensions) {
if (list.indexOf(cpu) !== -1) {
- return inst.cpu["AVX512VL"] ? cpu + "-VL" : cpu;
+ return inst.extensions["AVX512_VL"] ? cpu + "-VL" : cpu;
}
}
return "";
@@ -1981,7 +1768,7 @@ main();
"vm32z3": "vz_ptr"
};
- x86db.forEach(function(name, inst) {
+ isa.forEach(function(name, inst) {
if (getAVX512Flag(inst)) {
var operands = inst.operands;
var iops = [];
@@ -2012,10 +1799,10 @@ main();
else
flags = flags + (avx512Flags.length ? "{" + avx512Flags.join("|") + "}" : "");
}
- else if (inst.cpu.AVX2) {
+ else if (inst.extensions.AVX2) {
flags = "AVX2";
}
- else if (inst.cpu.AVX) {
+ else if (inst.extensions.AVX) {
flags = "AVX";
}
else {