From c119ecc79e19c630a8b1ef10fe01cc567901033f Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Mon, 5 Jun 2017 23:02:10 -0700 Subject: std::function is in You have to include it... Change-Id: Ia3e896da908f42939148fffd14c573086094939e Reviewed-by: Allan Sandfeld Jensen --- Source/JavaScriptCore/inspector/InspectorBackendDispatcher.h | 1 + Source/WebCore/css/CSSValue.h | 1 + Source/WebCore/css/StyleSheetContents.h | 1 + Source/WebCore/loader/NetscapePlugInStreamLoader.h | 1 + Source/WebCore/loader/ResourceLoader.h | 1 + 5 files changed, 5 insertions(+) diff --git a/Source/JavaScriptCore/inspector/InspectorBackendDispatcher.h b/Source/JavaScriptCore/inspector/InspectorBackendDispatcher.h index d86ad3eea..2ebfe384d 100644 --- a/Source/JavaScriptCore/inspector/InspectorBackendDispatcher.h +++ b/Source/JavaScriptCore/inspector/InspectorBackendDispatcher.h @@ -32,6 +32,7 @@ #include #include #include +#include namespace Inspector { diff --git a/Source/WebCore/css/CSSValue.h b/Source/WebCore/css/CSSValue.h index 59dc61744..4b7edc785 100644 --- a/Source/WebCore/css/CSSValue.h +++ b/Source/WebCore/css/CSSValue.h @@ -27,6 +27,7 @@ #include #include #include +#include namespace WebCore { diff --git a/Source/WebCore/css/StyleSheetContents.h b/Source/WebCore/css/StyleSheetContents.h index f25662172..376e47951 100644 --- a/Source/WebCore/css/StyleSheetContents.h +++ b/Source/WebCore/css/StyleSheetContents.h @@ -30,6 +30,7 @@ #include #include #include +#include namespace WebCore { diff --git a/Source/WebCore/loader/NetscapePlugInStreamLoader.h b/Source/WebCore/loader/NetscapePlugInStreamLoader.h index 9926c3312..0abadacc5 100644 --- a/Source/WebCore/loader/NetscapePlugInStreamLoader.h +++ b/Source/WebCore/loader/NetscapePlugInStreamLoader.h @@ -31,6 +31,7 @@ #include "ResourceLoader.h" #include +#include namespace WebCore { diff --git a/Source/WebCore/loader/ResourceLoader.h b/Source/WebCore/loader/ResourceLoader.h index 189b3bc8a..649ddbc02 100644 --- a/Source/WebCore/loader/ResourceLoader.h +++ b/Source/WebCore/loader/ResourceLoader.h @@ -35,6 +35,7 @@ #include "ResourceRequest.h" #include "ResourceResponse.h" #include +#include namespace WTF { class SchedulePair; -- cgit v1.2.3 From aab669a05f943c587f6acccd94d53a8544170c1c Mon Sep 17 00:00:00 2001 From: Konstantin Tokarev Date: Thu, 15 Jun 2017 12:13:20 +0300 Subject: Import WebKit commit 6d0ad27b6bc4209fb8d8cee2692dc0c6a5462051 Change-Id: Ifdedb7bc3162434686201813dc1d994cf5ae7e70 Reviewed-by: Konstantin Tokarev --- Source/JavaScriptCore/jsc.cpp | 8 +-- Source/JavaScriptCore/runtime/DateConversion.cpp | 3 +- Source/JavaScriptCore/runtime/JSArrayBufferView.h | 2 +- .../runtime/JSTypedArrayViewConstructor.cpp | 1 + Source/PlatformQt.cmake | 14 ++++ Source/WTF/wtf/Compiler.h | 11 +++- Source/WTF/wtf/PlatformQt.cmake | 2 + Source/WTF/wtf/text/win/WCharStringExtras.h | 70 ++++++++++++++++++++ Source/WebCore/PlatformQt.cmake | 16 +++++ Source/WebCore/bindings/js/ScriptController.cpp | 42 +++++++----- Source/WebCore/bindings/js/ScriptController.h | 5 +- .../ContentExtensionStyleSheet.cpp | 7 +- .../contentextensions/ContentExtensionStyleSheet.h | 3 +- Source/WebCore/dom/Document.cpp | 2 + Source/WebCore/dom/InlineStyleSheetOwner.cpp | 4 +- .../WebCore/editing/AlternativeTextController.cpp | 4 +- Source/WebCore/editing/Editor.cpp | 13 +++- Source/WebCore/editing/EditorCommand.cpp | 3 +- Source/WebCore/editing/TypingCommand.cpp | 4 +- Source/WebCore/loader/DocumentWriter.cpp | 6 ++ Source/WebCore/loader/FrameLoader.cpp | 5 +- Source/WebCore/page/ContextMenuController.cpp | 4 +- Source/WebCore/page/DOMSelection.cpp | 16 +++-- Source/WebCore/page/DragController.cpp | 4 +- Source/WebCore/page/EventHandler.cpp | 4 +- Source/WebCore/page/Frame.cpp | 9 +++ Source/WebCore/page/Frame.h | 3 + Source/WebCore/page/FrameView.cpp | 4 +- Source/WebCore/page/TextIndicator.cpp | 4 +- .../win/MediaPlayerPrivateMediaFoundation.cpp | 76 ++++++++++++++++------ .../win/MediaPlayerPrivateMediaFoundation.h | 7 ++ .../WebCore/platform/mock/mediasource/MockBox.cpp | 1 + Source/WebCore/rendering/RenderBlock.cpp | 8 ++- Source/WebCore/rendering/RenderBlock.h | 3 +- Source/WebCore/rendering/RenderBox.cpp | 46 +++++++++---- Source/WebCore/rendering/RenderListItem.cpp | 2 +- Source/WebCore/rendering/RenderRubyRun.cpp | 2 +- Source/WebCore/rendering/RenderRubyRun.h | 4 +- Source/WebCore/rendering/RenderTable.cpp | 2 +- Source/WebCore/rendering/RenderTable.h | 4 +- Source/WebCore/rendering/RenderView.cpp | 5 ++ Source/WebCore/rendering/RenderView.h | 9 ++- Source/WebCore/rendering/svg/RenderSVGText.cpp | 2 +- Source/WebCore/rendering/svg/RenderSVGText.h | 4 +- Source/WebCore/style/StyleTreeResolver.cpp | 10 +++ Source/WebKit/qt/declarative/CMakeLists.txt | 2 + .../qt/declarative/experimental/CMakeLists.txt | 2 + Source/WebKit/qt/tests/CMakeLists.txt | 2 +- Source/WebKit/win/Plugins/PluginDatabaseWin.cpp | 41 ++++++------ Source/WebKit/win/Plugins/PluginPackageWin.cpp | 14 ++-- Source/WebKit/win/Plugins/PluginViewWin.cpp | 5 +- .../WebKit2/Platform/IPC/unix/ConnectionUnix.cpp | 11 +++- Source/WebKit2/Shared/qt/NativeWebTouchEventQt.cpp | 4 ++ .../WebKit2/UIProcess/API/qt/tests/CMakeLists.txt | 2 + .../UserContent/WebUserContentControllerProxy.cpp | 4 +- Source/WebKit2/UIProcess/qt/QtPageClient.cpp | 2 + Source/WebKit2/UIProcess/qt/QtPageClient.h | 2 + .../WebKit2/UIProcess/qt/QtWebPageEventHandler.cpp | 21 ++++++ .../DOM/InjectedBundleRangeHandle.cpp | 4 +- .../WebCoreSupport/qt/WebDragClientQt.cpp | 4 ++ Source/WebKit2/WebProcess/WebPage/WebPage.cpp | 4 ++ Source/cmake/OptionsCommon.cmake | 10 ++- Source/cmake/OptionsQt.cmake | 45 ++++++++++++- Source/cmake/WebKitMacros.cmake | 8 ++- Tools/DumpRenderTree/CMakeLists.txt | 4 ++ Tools/MiniBrowser/qt/CMakeLists.txt | 2 +- Tools/QtTestBrowser/CMakeLists.txt | 2 +- Tools/QtTestBrowser/launcherwindow.cpp | 9 +++ Tools/QtTestBrowser/launcherwindow.h | 1 + Tools/qt/jhbuild.modules | 7 +- Tools/qt/manifest.txt | 1 + 71 files changed, 535 insertions(+), 136 deletions(-) create mode 100644 Source/WTF/wtf/text/win/WCharStringExtras.h diff --git a/Source/JavaScriptCore/jsc.cpp b/Source/JavaScriptCore/jsc.cpp index d9f888fb1..c0a84fc5f 100644 --- a/Source/JavaScriptCore/jsc.cpp +++ b/Source/JavaScriptCore/jsc.cpp @@ -68,6 +68,7 @@ #if OS(WINDOWS) #include +#include #else #include #endif @@ -868,8 +869,7 @@ static bool currentWorkingDirectory(DirectoryName& directoryName) // https://msdn.microsoft.com/en-us/library/windows/desktop/ff381407.aspx auto buffer = std::make_unique(bufferLength); DWORD lengthNotIncludingNull = ::GetCurrentDirectoryW(bufferLength, buffer.get()); - static_assert(sizeof(wchar_t) == sizeof(UChar), "In Windows, both are UTF-16LE"); - String directoryString = String(reinterpret_cast(buffer.get())); + String directoryString = wcharToString(buffer.get(), lengthNotIncludingNull); // We don't support network path like \\host\share\. if (directoryString.startsWith("\\\\")) return false; @@ -999,9 +999,7 @@ static bool fetchModuleFromLocalFileSystem(const String& fileName, Vector& // https://msdn.microsoft.com/en-us/library/windows/desktop/aa365247.aspx#maxpath // Use long UNC to pass the long path name to the Windows APIs. String longUNCPathName = WTF::makeString("\\\\?\\", fileName); - static_assert(sizeof(wchar_t) == sizeof(UChar), "In Windows, both are UTF-16LE"); - auto utf16Vector = longUNCPathName.charactersWithNullTermination(); - FILE* f = _wfopen(reinterpret_cast(utf16Vector.data()), L"rb"); + FILE* f = _wfopen(stringToNullTerminatedWChar(longUNCPathName).data(), L"rb"); #else FILE* f = fopen(fileName.utf8().data(), "r"); #endif diff --git a/Source/JavaScriptCore/runtime/DateConversion.cpp b/Source/JavaScriptCore/runtime/DateConversion.cpp index 05e27338b..8a87cc62a 100644 --- a/Source/JavaScriptCore/runtime/DateConversion.cpp +++ b/Source/JavaScriptCore/runtime/DateConversion.cpp @@ -32,6 +32,7 @@ #if OS(WINDOWS) #include +#include #endif using namespace WTF; @@ -108,7 +109,7 @@ String formatDateTime(const GregorianDateTime& t, DateTimeFormat format, bool as TIME_ZONE_INFORMATION timeZoneInformation; GetTimeZoneInformation(&timeZoneInformation); const WCHAR* winTimeZoneName = t.isDST() ? timeZoneInformation.DaylightName : timeZoneInformation.StandardName; - String timeZoneName(reinterpret_cast(winTimeZoneName)); + String timeZoneName = nullTerminatedWCharToString(winTimeZoneName); #else struct tm gtm = t; char timeZoneName[70]; diff --git a/Source/JavaScriptCore/runtime/JSArrayBufferView.h b/Source/JavaScriptCore/runtime/JSArrayBufferView.h index 769150b36..a5afdb9ef 100644 --- a/Source/JavaScriptCore/runtime/JSArrayBufferView.h +++ b/Source/JavaScriptCore/runtime/JSArrayBufferView.h @@ -162,7 +162,7 @@ public: bool isNeutered() { return hasArrayBuffer() && !vector(); } void neuter(); - void* vector() + void* vector() const { return m_vector.getPredicated( this, diff --git a/Source/JavaScriptCore/runtime/JSTypedArrayViewConstructor.cpp b/Source/JavaScriptCore/runtime/JSTypedArrayViewConstructor.cpp index bf99dbc87..5c038c502 100644 --- a/Source/JavaScriptCore/runtime/JSTypedArrayViewConstructor.cpp +++ b/Source/JavaScriptCore/runtime/JSTypedArrayViewConstructor.cpp @@ -35,6 +35,7 @@ #include "JSObject.h" #include "JSTypedArrayViewPrototype.h" #include "JSTypedArrays.h" +#include "TypedArrayInlines.h" namespace JSC { diff --git a/Source/PlatformQt.cmake b/Source/PlatformQt.cmake index 1bab6fbe5..0044dec03 100644 --- a/Source/PlatformQt.cmake +++ b/Source/PlatformQt.cmake @@ -1,3 +1,17 @@ +# Automoc + +set(TARGETS_WITH_AUTOMOC + WebKit + WebKitWidgets +) +if (ENABLE_WEBKIT2) + list(APPEND TARGETS_WITH_AUTOMOC + WebKit2 + ) +endif () +set_property(TARGET ${TARGETS_WITH_AUTOMOC} PROPERTY AUTOMOC ON) + + # Minimal debug # Builds with debug flags result in a huge amount of symbols with the GNU toolchain, diff --git a/Source/WTF/wtf/Compiler.h b/Source/WTF/wtf/Compiler.h index 89f4ca42e..f74fc8a0d 100644 --- a/Source/WTF/wtf/Compiler.h +++ b/Source/WTF/wtf/Compiler.h @@ -52,7 +52,6 @@ #define WTF_COMPILER_SUPPORTS_C_STATIC_ASSERT __has_feature(c_static_assert) #define WTF_COMPILER_SUPPORTS_CXX_REFERENCE_QUALIFIED_FUNCTIONS __has_feature(cxx_reference_qualified_functions) #define WTF_COMPILER_SUPPORTS_CXX_USER_LITERALS __has_feature(cxx_user_literals) -#define WTF_COMPILER_SUPPORTS_FALLTHROUGH_WARNINGS __has_feature(cxx_attributes) && __has_warning("-Wimplicit-fallthrough") #endif /* COMPILER(GCC_OR_CLANG) - GNU Compiler Collection or Clang */ @@ -176,10 +175,18 @@ /* FALLTHROUGH */ -#if !defined(FALLTHROUGH) && COMPILER_SUPPORTS(FALLTHROUGH_WARNINGS) && COMPILER(CLANG) +#if !defined(FALLTHROUGH) && defined(__cplusplus) && defined(__has_cpp_attribute) + +#if __has_cpp_attribute(fallthrough) +#define FALLTHROUGH [[fallthrough]] +#elif __has_cpp_attribute(clang::fallthrough) #define FALLTHROUGH [[clang::fallthrough]] +#elif __has_cpp_attribute(gnu::fallthrough) +#define FALLTHROUGH [[gnu::fallthrough]] #endif +#endif // !defined(FALLTHROUGH) && defined(__cplusplus) && defined(__has_cpp_attribute) + #if !defined(FALLTHROUGH) #define FALLTHROUGH #endif diff --git a/Source/WTF/wtf/PlatformQt.cmake b/Source/WTF/wtf/PlatformQt.cmake index 636ad40c2..32c8d2c70 100644 --- a/Source/WTF/wtf/PlatformQt.cmake +++ b/Source/WTF/wtf/PlatformQt.cmake @@ -4,6 +4,7 @@ list(APPEND WTF_SOURCES text/qt/StringQt.cpp ) +QTWEBKIT_GENERATE_MOC_FILES_CPP(qt/MainThreadQt.cpp qt/RunLoopQt.cpp) list(APPEND WTF_SYSTEM_INCLUDE_DIRECTORIES ${Qt5Core_INCLUDE_DIRS} @@ -32,6 +33,7 @@ if (UNIX AND NOT APPLE) qt/WorkQueueQt.cpp ) + QTWEBKIT_GENERATE_MOC_FILES_CPP(qt/WorkQueueQt.cpp) endif () if (USE_GLIB) diff --git a/Source/WTF/wtf/text/win/WCharStringExtras.h b/Source/WTF/wtf/text/win/WCharStringExtras.h new file mode 100644 index 000000000..9d004e515 --- /dev/null +++ b/Source/WTF/wtf/text/win/WCharStringExtras.h @@ -0,0 +1,70 @@ +/* + * Copyright (C) 2017 Konstantin Tokarev + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, + * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF + * THE POSSIBILITY OF SUCH DAMAGE. + */ + +#pragma once + +#include +#include + +namespace WTF { + +inline Vector stringToNullTerminatedWChar(const String& string) +{ + Vector result; + + if (!string.isNull()) { + result.reserveInitialCapacity(string.impl()->length() + 1); + + if (string.is8Bit()) { + const LChar* characters8 = string.impl()->characters8(); + for (size_t i = 0; i < string.impl()->length(); ++i) + result.uncheckedAppend(characters8[i]); + } else { + const UChar* characters16 = string.impl()->characters16(); + result.append(characters16, string.impl()->length()); + } + + result.append(0); + } + + return result; +} + +inline String wcharToString(const wchar_t* characters, unsigned length) +{ + static_assert(sizeof(wchar_t) == sizeof(UChar), "We assume wchar_t and UChar have the same size"); + return String(reinterpret_cast(characters), length); +} + +inline String nullTerminatedWCharToString(const wchar_t* characters) +{ + return wcharToString(characters, wcslen(characters) - 1); +} + +} // namespace WTF + +using WTF::stringToNullTerminatedWChar; +using WTF::wcharToString; +using WTF::nullTerminatedWCharToString; diff --git a/Source/WebCore/PlatformQt.cmake b/Source/WebCore/PlatformQt.cmake index 44ed482fb..c5466b6c7 100644 --- a/Source/WebCore/PlatformQt.cmake +++ b/Source/WebCore/PlatformQt.cmake @@ -162,6 +162,20 @@ list(APPEND WebCore_SOURCES platform/text/qt/TextBreakIteratorInternalICUQt.cpp ) +QTWEBKIT_GENERATE_MOC_FILES_CPP( + platform/network/qt/DNSQt.cpp + platform/qt/MainThreadSharedTimerQt.cpp +) + +QTWEBKIT_GENERATE_MOC_FILES_H( + platform/network/qt/CookieJarQt.h + platform/network/qt/QNetworkReplyHandler.h + platform/network/qt/QtMIMETypeSniffer.h +) + +QTWEBKIT_GENERATE_MOC_FILE_H(platform/network/qt/NetworkStateNotifierPrivate.h platform/network/qt/NetworkStateNotifierQt.cpp) +QTWEBKIT_GENERATE_MOC_FILE_H(platform/network/qt/SocketStreamHandlePrivate.h platform/network/qt/SocketStreamHandleQt.cpp) + if (COMPILER_IS_GCC_OR_CLANG) set_source_files_properties( platform/graphics/qt/ImageBufferDataQt.cpp @@ -183,6 +197,7 @@ if (ENABLE_GAMEPAD_DEPRECATED) list(APPEND WebCore_SOURCES platform/qt/GamepadsQt.cpp ) + QTWEBKIT_GENERATE_MOC_FILES_CPP(platform/qt/GamepadsQt.cpp) endif () if (ENABLE_GRAPHICS_CONTEXT_3D) @@ -359,6 +374,7 @@ if (USE_QT_MULTIMEDIA) list(APPEND WebCore_LIBRARIES ${Qt5Multimedia_LIBRARIES} ) + QTWEBKIT_GENERATE_MOC_FILES_H(platform/graphics/qt/MediaPlayerPrivateQt.h) endif () if (ENABLE_VIDEO) diff --git a/Source/WebCore/bindings/js/ScriptController.cpp b/Source/WebCore/bindings/js/ScriptController.cpp index 1bd6efcac..93bbd3cc4 100644 --- a/Source/WebCore/bindings/js/ScriptController.cpp +++ b/Source/WebCore/bindings/js/ScriptController.cpp @@ -1,7 +1,7 @@ /* * Copyright (C) 1999-2001 Harri Porten (porten@kde.org) * Copyright (C) 2001 Peter Kelly (pmk@post.com) - * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved. + * Copyright (C) 2006-2008, 2016 Apple Inc. All rights reserved. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public @@ -197,7 +197,7 @@ void ScriptController::getAllWorlds(Vector>& worlds) static_cast(JSDOMWindow::commonVM().clientData)->getAllWorlds(worlds); } -void ScriptController::clearWindowShell(DOMWindow* newDOMWindow, bool goingIntoPageCache) +void ScriptController::clearWindowShellsNotMatchingDOMWindow(DOMWindow* newDOMWindow, bool goingIntoPageCache) { if (m_windowShells.isEmpty()) return; @@ -205,16 +205,13 @@ void ScriptController::clearWindowShell(DOMWindow* newDOMWindow, bool goingIntoP JSLockHolder lock(JSDOMWindowBase::commonVM()); Vector> windowShells = this->windowShells(); - for (size_t i = 0; i < windowShells.size(); ++i) { - JSDOMWindowShell* windowShell = windowShells[i].get(); - + for (auto& windowShell : windowShells) { if (&windowShell->window()->wrapped() == newDOMWindow) continue; // Clear the debugger and console from the current window before setting the new window. - attachDebugger(windowShell, nullptr); + attachDebugger(windowShell.get(), nullptr); windowShell->window()->setConsoleClient(nullptr); - // FIXME: We should clear console profiles for each frame as soon as the frame is destroyed. // Instead of clearing all of them when the main frame is destroyed. if (m_frame.isMainFrame()) { @@ -223,24 +220,39 @@ void ScriptController::clearWindowShell(DOMWindow* newDOMWindow, bool goingIntoP } windowShell->window()->willRemoveFromWindowShell(); - windowShell->setWindow(newDOMWindow); + } + + // It's likely that resetting our windows created a lot of garbage, unless + // it went in a back/forward cache. + if (!goingIntoPageCache) + collectGarbageAfterWindowShellDestruction(); +} +void ScriptController::setDOMWindowForWindowShell(DOMWindow* newDOMWindow) +{ + if (m_windowShells.isEmpty()) + return; + + JSLockHolder lock(JSDOMWindowBase::commonVM()); + + Vector> windowShells = this->windowShells(); + for (auto& windowShell : windowShells) { + if (&windowShell->window()->wrapped() == newDOMWindow) + continue; + + windowShell->setWindow(newDOMWindow); + // An m_cacheableBindingRootObject persists between page navigations // so needs to know about the new JSDOMWindow. if (m_cacheableBindingRootObject) m_cacheableBindingRootObject->updateGlobalObject(windowShell->window()); - + if (Page* page = m_frame.page()) { - attachDebugger(windowShell, page->debugger()); + attachDebugger(windowShell.get(), page->debugger()); windowShell->window()->setProfileGroup(page->group().identifier()); windowShell->window()->setConsoleClient(&page->console()); } } - - // It's likely that resetting our windows created a lot of garbage, unless - // it went in a back/forward cache. - if (!goingIntoPageCache) - collectGarbageAfterWindowShellDestruction(); } JSDOMWindowShell* ScriptController::initScript(DOMWrapperWorld& world) diff --git a/Source/WebCore/bindings/js/ScriptController.h b/Source/WebCore/bindings/js/ScriptController.h index 62a51b855..6f65c722e 100644 --- a/Source/WebCore/bindings/js/ScriptController.h +++ b/Source/WebCore/bindings/js/ScriptController.h @@ -1,7 +1,7 @@ /* * Copyright (C) 1999 Harri Porten (porten@kde.org) * Copyright (C) 2001 Peter Kelly (pmk@post.com) - * Copyright (C) 2008 Apple Inc. All rights reserved. + * Copyright (C) 2008, 2016 Apple Inc. All rights reserved. * Copyright (C) 2008 Eric Seidel * * This library is free software; you can redistribute it and/or @@ -135,7 +135,8 @@ public: const String* sourceURL() const { return m_sourceURL; } // 0 if we are not evaluating any script - void clearWindowShell(DOMWindow* newDOMWindow, bool goingIntoPageCache); + void clearWindowShellsNotMatchingDOMWindow(DOMWindow* newDOMWindow, bool goingIntoPageCache); + void setDOMWindowForWindowShell(DOMWindow* newDOMWindow); void updateDocument(); void namedItemAdded(HTMLDocument*, const AtomicString&) { } diff --git a/Source/WebCore/contentextensions/ContentExtensionStyleSheet.cpp b/Source/WebCore/contentextensions/ContentExtensionStyleSheet.cpp index d3126773f..44d7c5738 100644 --- a/Source/WebCore/contentextensions/ContentExtensionStyleSheet.cpp +++ b/Source/WebCore/contentextensions/ContentExtensionStyleSheet.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2015 Apple Inc. All rights reserved. + * Copyright (C) 2015-2016 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -43,6 +43,11 @@ ContentExtensionStyleSheet::ContentExtensionStyleSheet(Document& document) m_styleSheet->contents().setIsUserStyleSheet(true); } +ContentExtensionStyleSheet::~ContentExtensionStyleSheet() +{ + m_styleSheet->clearOwnerNode(); +} + bool ContentExtensionStyleSheet::addDisplayNoneSelector(const String& selector, uint32_t selectorID) { ASSERT(selectorID != std::numeric_limits::max()); diff --git a/Source/WebCore/contentextensions/ContentExtensionStyleSheet.h b/Source/WebCore/contentextensions/ContentExtensionStyleSheet.h index a503b586a..514407676 100644 --- a/Source/WebCore/contentextensions/ContentExtensionStyleSheet.h +++ b/Source/WebCore/contentextensions/ContentExtensionStyleSheet.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2015 Apple Inc. All rights reserved. + * Copyright (C) 2015-2016 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -45,6 +45,7 @@ public: { return adoptRef(*new ContentExtensionStyleSheet(document)); } + virtual ~ContentExtensionStyleSheet(); bool addDisplayNoneSelector(const String& selector, uint32_t selectorID); diff --git a/Source/WebCore/dom/Document.cpp b/Source/WebCore/dom/Document.cpp index f34a1c15f..2598b0f1e 100644 --- a/Source/WebCore/dom/Document.cpp +++ b/Source/WebCore/dom/Document.cpp @@ -1769,6 +1769,8 @@ void Document::scheduleForcedStyleRecalc() void Document::scheduleStyleRecalc() { + ASSERT(!m_renderView || !m_renderView->inHitTesting()); + if (m_styleRecalcTimer.isActive() || inPageCache()) return; diff --git a/Source/WebCore/dom/InlineStyleSheetOwner.cpp b/Source/WebCore/dom/InlineStyleSheetOwner.cpp index e6e7acdb0..83574842c 100644 --- a/Source/WebCore/dom/InlineStyleSheetOwner.cpp +++ b/Source/WebCore/dom/InlineStyleSheetOwner.cpp @@ -1,6 +1,6 @@ /* * Copyright (C) 2006, 2007 Rob Buis - * Copyright (C) 2008, 2013 Apple, Inc. All rights reserved. + * Copyright (C) 2008-2016 Apple, Inc. All rights reserved. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public @@ -46,6 +46,8 @@ InlineStyleSheetOwner::InlineStyleSheetOwner(Document& document, bool createdByP InlineStyleSheetOwner::~InlineStyleSheetOwner() { + if (m_sheet) + clearSheet(); } static AuthorStyleSheets& authorStyleSheetsForElement(Element& element) diff --git a/Source/WebCore/editing/AlternativeTextController.cpp b/Source/WebCore/editing/AlternativeTextController.cpp index 73102571a..32c204d14 100644 --- a/Source/WebCore/editing/AlternativeTextController.cpp +++ b/Source/WebCore/editing/AlternativeTextController.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved. + * Copyright (C) 2006-2008, 2016 Apple Inc. All rights reserved. * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies) * * Redistribution and use in source and binary forms, with or without @@ -315,6 +315,8 @@ void AlternativeTextController::respondToUnappliedSpellCorrection(const VisibleS { if (AlternativeTextClient* client = alternativeTextClient()) client->recordAutocorrectionResponse(AutocorrectionReverted, corrected, correction); + + Ref protector(m_frame); m_frame.document()->updateLayout(); m_frame.selection().setSelection(selectionOfCorrected, FrameSelection::defaultSetSelectionOptions() | FrameSelection::SpellCorrectionTriggered); RefPtr range = Range::create(*m_frame.document(), m_frame.selection().selection().start(), m_frame.selection().selection().end()); diff --git a/Source/WebCore/editing/Editor.cpp b/Source/WebCore/editing/Editor.cpp index cdbfbda74..41a9730ab 100644 --- a/Source/WebCore/editing/Editor.cpp +++ b/Source/WebCore/editing/Editor.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2006, 2007, 2008, 2011, 2013-2015 Apple Inc. All rights reserved. + * Copyright (C) 2006-2008, 2011, 2013-2016 Apple Inc. All rights reserved. * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies) * * Redistribution and use in source and binary forms, with or without @@ -1743,6 +1743,8 @@ void Editor::setComposition(const String& text, SetCompositionMode mode) void Editor::setComposition(const String& text, const Vector& underlines, unsigned selectionStart, unsigned selectionEnd) { + Ref protection(m_frame); + UserTypingGestureIndicator typingGestureIndicator(m_frame); setIgnoreCompositionSelectionChange(true); @@ -1876,6 +1878,8 @@ void Editor::learnSpelling() #if !PLATFORM(IOS) void Editor::advanceToNextMisspelling(bool startBeforeSelection) { + Ref protection(m_frame); + // The basic approach is to search in two phases - from the selection end to the end of the doc, and // then we wrap and search from the doc start to (approximately) where we started. @@ -2191,6 +2195,8 @@ void Editor::markMisspellingsAndBadGrammar(const VisibleSelection &movingSelecti void Editor::markMisspellingsAfterTypingToWord(const VisiblePosition &wordStart, const VisibleSelection& selectionAfterTyping, bool doReplacement) { + Ref protection(m_frame); + #if PLATFORM(IOS) UNUSED_PARAM(selectionAfterTyping); UNUSED_PARAM(doReplacement); @@ -2437,6 +2443,7 @@ static void correctSpellcheckingPreservingTextCheckingParagraph(TextCheckingPara void Editor::markAndReplaceFor(PassRefPtr request, const Vector& results) { + Ref protection(m_frame); ASSERT(request); TextCheckingTypeMask textCheckingOptions = request->data().mask(); @@ -2889,6 +2896,8 @@ void Editor::dismissCorrectionPanelAsIgnored() void Editor::changeSelectionAfterCommand(const VisibleSelection& newSelection, FrameSelection::SetSelectionOptions options, AXTextStateChangeIntent intent) { + Ref protection(m_frame); + // If the new selection is orphaned, then don't update the selection. if (newSelection.start().isOrphan() || newSelection.end().isOrphan()) return; @@ -3079,6 +3088,8 @@ void Editor::applyEditingStyleToElement(Element* element) const bool Editor::findString(const String& target, FindOptions options) { + Ref protection(m_frame); + VisibleSelection selection = m_frame.selection().selection(); RefPtr resultRange = rangeOfString(target, selection.firstRange().get(), options); diff --git a/Source/WebCore/editing/EditorCommand.cpp b/Source/WebCore/editing/EditorCommand.cpp index 82e5daa66..92674c58a 100644 --- a/Source/WebCore/editing/EditorCommand.cpp +++ b/Source/WebCore/editing/EditorCommand.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2006, 2007, 2008, 2014 Apple Inc. All rights reserved. + * Copyright (C) 2006-2008, 2014, 2016 Apple Inc. All rights reserved. * Copyright (C) 2008 Nokia Corporation and/or its subsidiary(-ies) * Copyright (C) 2009 Igalia S.L. * @@ -1064,6 +1064,7 @@ static bool executeSuperscript(Frame& frame, Event*, EditorCommandSource source, static bool executeSwapWithMark(Frame& frame, Event*, EditorCommandSource, const String&) { + Ref protector(frame); const VisibleSelection& mark = frame.editor().mark(); const VisibleSelection& selection = frame.selection().selection(); if (mark.isNone() || selection.isNone()) { diff --git a/Source/WebCore/editing/TypingCommand.cpp b/Source/WebCore/editing/TypingCommand.cpp index a0f912ab0..f8b4509df 100644 --- a/Source/WebCore/editing/TypingCommand.cpp +++ b/Source/WebCore/editing/TypingCommand.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2005, 2006, 2007, 2008 Apple Inc. All rights reserved. + * Copyright (C) 2005-2008, 2016 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -438,6 +438,7 @@ bool TypingCommand::makeEditableRootEmpty() void TypingCommand::deleteKeyPressed(TextGranularity granularity, bool shouldAddToKillRing) { Frame& frame = this->frame(); + Ref protector(frame); frame.editor().updateMarkersForWordsAffectedByEditing(false); @@ -547,6 +548,7 @@ void TypingCommand::deleteKeyPressed(TextGranularity granularity, bool shouldAdd void TypingCommand::forwardDeleteKeyPressed(TextGranularity granularity, bool shouldAddToKillRing) { Frame& frame = this->frame(); + Ref protector(frame); frame.editor().updateMarkersForWordsAffectedByEditing(false); diff --git a/Source/WebCore/loader/DocumentWriter.cpp b/Source/WebCore/loader/DocumentWriter.cpp index 442e3bf57..593c0a5e7 100644 --- a/Source/WebCore/loader/DocumentWriter.cpp +++ b/Source/WebCore/loader/DocumentWriter.cpp @@ -71,6 +71,12 @@ DocumentWriter::DocumentWriter(Frame* frame) void DocumentWriter::replaceDocument(const String& source, Document* ownerDocument) { m_frame->loader().stopAllLoaders(); + + // If we are in the midst of changing the frame's document, don't execute script + // that modifes the document further: + if (m_frame->documentIsBeingReplaced()) + return; + begin(m_frame->document()->url(), true, ownerDocument); // begin() might fire an unload event, which will result in a situation where no new document has been attached, diff --git a/Source/WebCore/loader/FrameLoader.cpp b/Source/WebCore/loader/FrameLoader.cpp index 705b0f5a5..1d6c60ba5 100644 --- a/Source/WebCore/loader/FrameLoader.cpp +++ b/Source/WebCore/loader/FrameLoader.cpp @@ -591,7 +591,7 @@ void FrameLoader::clear(Document* newDocument, bool clearWindowProperties, bool if (clearWindowProperties) { InspectorInstrumentation::frameWindowDiscarded(&m_frame, m_frame.document()->domWindow()); m_frame.document()->domWindow()->resetUnlessSuspendedForDocumentSuspension(); - m_frame.script().clearWindowShell(newDocument->domWindow(), m_frame.document()->inPageCache()); + m_frame.script().clearWindowShellsNotMatchingDOMWindow(newDocument->domWindow(), m_frame.document()->inPageCache()); } m_frame.selection().prepareForDestruction(); @@ -609,6 +609,9 @@ void FrameLoader::clear(Document* newDocument, bool clearWindowProperties, bool subframeLoader().clear(); + if (clearWindowProperties) + m_frame.script().setDOMWindowForWindowShell(newDocument->domWindow()); + if (clearScriptObjects) m_frame.script().clearScriptObjects(); diff --git a/Source/WebCore/page/ContextMenuController.cpp b/Source/WebCore/page/ContextMenuController.cpp index 47e5fc970..d528a92cd 100644 --- a/Source/WebCore/page/ContextMenuController.cpp +++ b/Source/WebCore/page/ContextMenuController.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2006, 2007 Apple Inc. All rights reserved. + * Copyright (C) 2006-2007, 2016 Apple Inc. All rights reserved. * Copyright (C) 2010 Igalia S.L * * Redistribution and use in source and binary forms, with or without @@ -223,6 +223,8 @@ void ContextMenuController::contextMenuItemSelected(ContextMenuAction action, co if (!frame) return; + Ref protector(*frame); + switch (action) { case ContextMenuItemTagOpenLinkInNewWindow: openNewWindow(m_context.hitTestResult().absoluteLinkURL(), frame, ShouldOpenExternalURLsPolicy::ShouldAllowExternalSchemes); diff --git a/Source/WebCore/page/DOMSelection.cpp b/Source/WebCore/page/DOMSelection.cpp index e119f64d8..064f76837 100644 --- a/Source/WebCore/page/DOMSelection.cpp +++ b/Source/WebCore/page/DOMSelection.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2007, 2009 Apple Inc. All rights reserved. + * Copyright (C) 2007, 2009, 2016 Apple Inc. All rights reserved. * Copyright (C) 2012 Google Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -203,7 +203,7 @@ void DOMSelection::collapse(Node* node, int offset, ExceptionCode& ec) if (!isValidForPosition(node)) return; - // FIXME: Eliminate legacy editing positions + Ref protector(*m_frame); m_frame->selection().moveTo(createLegacyEditingPosition(node, offset), DOWNSTREAM); } @@ -219,6 +219,7 @@ void DOMSelection::collapseToEnd(ExceptionCode& ec) return; } + Ref protector(*m_frame); m_frame->selection().moveTo(selection.end(), DOWNSTREAM); } @@ -234,6 +235,7 @@ void DOMSelection::collapseToStart(ExceptionCode& ec) return; } + Ref protector(*m_frame); m_frame->selection().moveTo(selection.start(), DOWNSTREAM); } @@ -257,7 +259,7 @@ void DOMSelection::setBaseAndExtent(Node* baseNode, int baseOffset, Node* extent if (!isValidForPosition(baseNode) || !isValidForPosition(extentNode)) return; - // FIXME: Eliminate legacy editing positions + Ref protector(*m_frame); m_frame->selection().moveTo(createLegacyEditingPosition(baseNode, baseOffset), createLegacyEditingPosition(extentNode, extentOffset), DOWNSTREAM); } @@ -273,7 +275,7 @@ void DOMSelection::setPosition(Node* node, int offset, ExceptionCode& ec) if (!isValidForPosition(node)) return; - // FIXME: Eliminate legacy editing positions + Ref protector(*m_frame); m_frame->selection().moveTo(createLegacyEditingPosition(node, offset), DOWNSTREAM); } @@ -324,6 +326,7 @@ void DOMSelection::modify(const String& alterString, const String& directionStri else return; + Ref protector(*m_frame); m_frame->selection().modify(alter, direction, granularity); } @@ -345,7 +348,7 @@ void DOMSelection::extend(Node* node, int offset, ExceptionCode& ec) if (!isValidForPosition(node)) return; - // FIXME: Eliminate legacy editing positions + Ref protector(*m_frame); m_frame->selection().setExtent(createLegacyEditingPosition(node, offset), DOWNSTREAM); } @@ -385,6 +388,8 @@ void DOMSelection::addRange(Range* r) if (!r) return; + Ref protector(*m_frame); + FrameSelection& selection = m_frame->selection(); if (selection.isNone()) { @@ -433,6 +438,7 @@ void DOMSelection::deleteFromDocument() if (!selectedRange) return; + Ref protector(*m_frame); selectedRange->deleteContents(ASSERT_NO_EXCEPTION); setBaseAndExtent(&selectedRange->startContainer(), selectedRange->startOffset(), &selectedRange->startContainer(), selectedRange->startOffset(), ASSERT_NO_EXCEPTION); diff --git a/Source/WebCore/page/DragController.cpp b/Source/WebCore/page/DragController.cpp index c4cbb67ef..7a874db56 100644 --- a/Source/WebCore/page/DragController.cpp +++ b/Source/WebCore/page/DragController.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2007, 2009, 2010, 2013, 2015 Apple Inc. All rights reserved. + * Copyright (C) 2007, 2009-2010, 2013, 2015-2016 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -432,6 +432,7 @@ DragOperation DragController::operationForLoad(DragData& dragData) static bool setSelectionToDragCaret(Frame* frame, VisibleSelection& dragCaret, RefPtr& range, const IntPoint& point) { + Ref protector(*frame); frame->selection().setSelection(dragCaret); if (frame->selection().selection().isNone()) { dragCaret = frame->visiblePositionForPoint(point); @@ -752,6 +753,7 @@ bool DragController::startDrag(Frame& src, const DragState& state, DragOperation if (!src.view() || !src.contentRenderer() || !state.source) return false; + Ref protector(src); HitTestResult hitTestResult = src.eventHandler().hitTestResultAtPoint(dragOrigin, HitTestRequest::ReadOnly | HitTestRequest::Active); // FIXME(136836): Investigate whether all elements should use the containsIncludingShadowDOM() path here. diff --git a/Source/WebCore/page/EventHandler.cpp b/Source/WebCore/page/EventHandler.cpp index a40b4bfab..97a0d2d39 100644 --- a/Source/WebCore/page/EventHandler.cpp +++ b/Source/WebCore/page/EventHandler.cpp @@ -1138,8 +1138,8 @@ HitTestResult EventHandler::hitTestResultAtPoint(const LayoutPoint& point, HitTe } // We should always start hit testing a clean tree. - if (m_frame.document()) - m_frame.document()->updateLayoutIgnorePendingStylesheets(); + if (auto* frameView = m_frame.view()) + frameView->updateLayoutAndStyleIfNeededRecursive(); HitTestResult result(point, padding.height(), padding.width(), padding.height(), padding.width()); RenderView* renderView = m_frame.contentRenderer(); if (!renderView) diff --git a/Source/WebCore/page/Frame.cpp b/Source/WebCore/page/Frame.cpp index 9315237af..f447d5ded 100644 --- a/Source/WebCore/page/Frame.cpp +++ b/Source/WebCore/page/Frame.cpp @@ -267,6 +267,11 @@ void Frame::setDocument(RefPtr&& newDocument) { ASSERT(!newDocument || newDocument->frame() == this); + if (m_documentIsBeingReplaced) + return; + + m_documentIsBeingReplaced = true; + if (m_doc && m_doc->pageCacheState() != Document::InPageCache) m_doc->prepareForDestruction(); @@ -280,6 +285,8 @@ void Frame::setDocument(RefPtr&& newDocument) newDocument->didBecomeCurrentDocumentInFrame(); InspectorInstrumentation::frameDocumentUpdated(this); + + m_documentIsBeingReplaced = false; } #if ENABLE(ORIENTATION_EVENTS) @@ -603,6 +610,8 @@ int Frame::checkOverflowScroll(OverflowScrollAction action) } } + Ref protectedThis(*this); + if (action == PerformOverflowScroll && (deltaX || deltaY)) { layer->scrollToOffset(layer->scrollOffset() + IntSize(deltaX, deltaY)); diff --git a/Source/WebCore/page/Frame.h b/Source/WebCore/page/Frame.h index d0e22ef4e..f43a93ecb 100644 --- a/Source/WebCore/page/Frame.h +++ b/Source/WebCore/page/Frame.h @@ -162,6 +162,8 @@ namespace WebCore { WEBCORE_EXPORT RenderView* contentRenderer() const; // Root of the render tree for the document contained in this frame. WEBCORE_EXPORT RenderWidget* ownerRenderer() const; // Renderer for the element that contains this frame. + bool documentIsBeingReplaced() const { return m_documentIsBeingReplaced; } + // ======== All public functions below this point are candidates to move out of Frame into another class. ======== void injectUserScripts(UserScriptInjectionTime); @@ -329,6 +331,7 @@ namespace WebCore { int m_activeDOMObjectsAndAnimationsSuspendedCount; bool m_mainFrameWasDestroyed { false }; + bool m_documentIsBeingReplaced { false }; protected: std::unique_ptr m_eventHandler; diff --git a/Source/WebCore/page/FrameView.cpp b/Source/WebCore/page/FrameView.cpp index bf35cf8b2..2983a2d92 100644 --- a/Source/WebCore/page/FrameView.cpp +++ b/Source/WebCore/page/FrameView.cpp @@ -2741,8 +2741,10 @@ void FrameView::setNeedsLayout() return; } - if (RenderView* renderView = this->renderView()) + if (auto* renderView = this->renderView()) { + ASSERT(!renderView->inHitTesting()); renderView->setNeedsLayout(); + } } void FrameView::unscheduleRelayout() diff --git a/Source/WebCore/page/TextIndicator.cpp b/Source/WebCore/page/TextIndicator.cpp index fd0c0ba73..768fd9aa7 100644 --- a/Source/WebCore/page/TextIndicator.cpp +++ b/Source/WebCore/page/TextIndicator.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2010, 2015 Apple Inc. All rights reserved. + * Copyright (C) 2010, 2015-2016 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -69,6 +69,8 @@ RefPtr TextIndicator::createWithRange(const Range& range, TextInd if (!frame) return nullptr; + Ref protector(*frame); + #if PLATFORM(IOS) frame->editor().setIgnoreCompositionSelectionChange(true); frame->selection().setUpdateAppearanceEnabled(true); diff --git a/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.cpp b/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.cpp index b6bdf60ca..0610c85b6 100644 --- a/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.cpp +++ b/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.cpp @@ -47,6 +47,7 @@ #include #include +#include SOFT_LINK_LIBRARY(Mf); SOFT_LINK_OPTIONAL(Mf, MFCreateSourceResolver, HRESULT, STDAPICALLTYPE, (IMFSourceResolver**)); @@ -98,6 +99,7 @@ MediaPlayerPrivateMediaFoundation::MediaPlayerPrivateMediaFoundation(MediaPlayer , m_hasVideo(false) , m_preparingToPlay(false) , m_hwndVideo(nullptr) + , m_volume(1.0) , m_networkState(MediaPlayer::Empty) , m_readyState(MediaPlayer::HaveNothing) , m_weakPtrFactory(this) @@ -147,7 +149,7 @@ static const HashSet& mimeTypeCache() if (SUCCEEDED(hr)) { CALPWSTR mimeTypeArray = propVarMimeTypeArray.calpwstr; for (unsigned i = 0; i < mimeTypeArray.cElems; i++) - cachedTypes.get().add(mimeTypeArray.pElems[i]); + cachedTypes.get().add(nullTerminatedWCharToString(mimeTypeArray.pElems[i])); } PropVariantClear(&propVarMimeTypeArray); @@ -173,6 +175,11 @@ MediaPlayer::SupportsType MediaPlayerPrivateMediaFoundation::supportsType(const void MediaPlayerPrivateMediaFoundation::load(const String& url) { + { + LockHolder locker(m_cachedNaturalSizeLock); + m_cachedNaturalSize = FloatSize(); + } + startCreateMediaSource(url); m_networkState = MediaPlayer::Loading; @@ -215,9 +222,10 @@ bool MediaPlayerPrivateMediaFoundation::supportsFullscreen() const return true; } -FloatSize MediaPlayerPrivateMediaFoundation::naturalSize() const +FloatSize MediaPlayerPrivateMediaFoundation::naturalSize() const { - return m_size; + LockHolder locker(m_cachedNaturalSizeLock); + return m_cachedNaturalSize; } bool MediaPlayerPrivateMediaFoundation::hasVideo() const @@ -299,16 +307,27 @@ bool MediaPlayerPrivateMediaFoundation::paused() const return m_paused; } -void MediaPlayerPrivateMediaFoundation::setVolume(float volume) +bool MediaPlayerPrivateMediaFoundation::setAllChannelVolumes(float volume) { if (!MFGetServicePtr()) - return; + return false; - COMPtr audioVolume; - if (SUCCEEDED(MFGetServicePtr()(m_mediaSession.get(), MR_POLICY_VOLUME_SERVICE, __uuidof(IMFSimpleAudioVolume), (void **)&audioVolume))) { - HRESULT hr = audioVolume->SetMasterVolume(volume); - ASSERT(SUCCEEDED(hr)); - } + COMPtr audioVolume; + if (!SUCCEEDED(MFGetServicePtr()(m_mediaSession.get(), MR_STREAM_VOLUME_SERVICE, __uuidof(IMFAudioStreamVolume), (void **)&audioVolume))) + return false; + + UINT32 channelsCount; + HRESULT hr = audioVolume->GetChannelCount(&channelsCount); + ASSERT(SUCCEEDED(hr)); + + Vector volumes(channelsCount, volume); + return SUCCEEDED(audioVolume->SetAllVolumes(channelsCount, volumes.data())); +} + +void MediaPlayerPrivateMediaFoundation::setVolume(float volume) +{ + if (setAllChannelVolumes(volume)) + m_volume = volume; } bool MediaPlayerPrivateMediaFoundation::supportsMuting() const @@ -318,14 +337,7 @@ bool MediaPlayerPrivateMediaFoundation::supportsMuting() const void MediaPlayerPrivateMediaFoundation::setMuted(bool muted) { - if (!MFGetServicePtr()) - return; - - COMPtr audioVolume; - if (SUCCEEDED(MFGetServicePtr()(m_mediaSession.get(), MR_POLICY_VOLUME_SERVICE, __uuidof(IMFSimpleAudioVolume), (void **)&audioVolume))) { - HRESULT hr = audioVolume->SetMute(muted ? TRUE : FALSE); - ASSERT(SUCCEEDED(hr)); - } + setAllChannelVolumes(muted ? 0.0 : m_volume); } MediaPlayer::NetworkState MediaPlayerPrivateMediaFoundation::networkState() const @@ -465,7 +477,7 @@ bool MediaPlayerPrivateMediaFoundation::startCreateMediaSource(const String& url return false; COMPtr cancelCookie; - Vector urlSource = url.charactersWithNullTermination(); + Vector urlSource = stringToNullTerminatedWChar(url); AsyncCallback* callback = new AsyncCallback(this, false); @@ -749,6 +761,12 @@ void MediaPlayerPrivateMediaFoundation::notifyDeleted() (*it)->onMediaPlayerDeleted(); } +void MediaPlayerPrivateMediaFoundation::setNaturalSize(const FloatSize& size) +{ + LockHolder locker(m_cachedNaturalSizeLock); + m_cachedNaturalSize = size; +} + bool MediaPlayerPrivateMediaFoundation::createOutputNode(COMPtr sourceSD, COMPtr& node) { if (!MFCreateTopologyNodePtr() || !MFCreateAudioRendererActivatePtr() || !MFCreateVideoRendererActivatePtr()) @@ -1554,6 +1572,22 @@ static bool areMediaTypesEqual(IMFMediaType* type1, IMFMediaType* type2) return S_OK == type1->IsEqual(type2, &flags); } +static FloatSize calculateNaturalSize(IMFMediaType* mediaType) +{ + UINT32 width = 0, height = 0; + HRESULT hr = MFGetAttributeSize(mediaType, MF_MT_FRAME_SIZE, &width, &height); + if (FAILED(hr) || !height) + return FloatSize(); + + UINT32 pixelAspectRatioNumerator = 0; + UINT32 pixelAspectRatioDenominator = 0; + hr = MFGetAttributeRatio(mediaType, MF_MT_PIXEL_ASPECT_RATIO, &pixelAspectRatioNumerator, &pixelAspectRatioDenominator); + if (SUCCEEDED(hr) && pixelAspectRatioNumerator && pixelAspectRatioDenominator) + return FloatSize(float(width) * pixelAspectRatioNumerator / pixelAspectRatioDenominator, height); + + return FloatSize(); +} + HRESULT MediaPlayerPrivateMediaFoundation::CustomVideoPresenter::setMediaType(IMFMediaType* mediaType) { if (!mediaType) { @@ -1611,6 +1645,10 @@ HRESULT MediaPlayerPrivateMediaFoundation::CustomVideoPresenter::setMediaType(IM m_scheduler.setFrameRate(defaultFrameRate); } + // Update natural size + if (m_mediaPlayer) + m_mediaPlayer->setNaturalSize(calculateNaturalSize(mediaType)); + ASSERT(mediaType); m_mediaType = mediaType; diff --git a/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.h b/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.h index 2fdce58ee..c3303cf7b 100644 --- a/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.h +++ b/Source/WebCore/platform/graphics/win/MediaPlayerPrivateMediaFoundation.h @@ -112,6 +112,7 @@ private: bool m_hasAudio; bool m_hasVideo; bool m_preparingToPlay; + float m_volume; HWND m_hwndVideo; MediaPlayer::NetworkState m_networkState; MediaPlayer::ReadyState m_readyState; @@ -121,6 +122,9 @@ private: HashSet m_listeners; Lock m_mutexListeners; + FloatSize m_cachedNaturalSize; + mutable Lock m_cachedNaturalSizeLock; + WeakPtrFactory m_weakPtrFactory; COMPtr m_mediaSession; COMPtr m_sourceResolver; @@ -158,10 +162,13 @@ private: void addListener(MediaPlayerListener*); void removeListener(MediaPlayerListener*); + void setNaturalSize(const FloatSize&); void notifyDeleted(); static LRESULT CALLBACK VideoViewWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam); + bool setAllChannelVolumes(float); + class MediaPlayerListener { public: MediaPlayerListener() { } diff --git a/Source/WebCore/platform/mock/mediasource/MockBox.cpp b/Source/WebCore/platform/mock/mediasource/MockBox.cpp index 31028030d..149827610 100644 --- a/Source/WebCore/platform/mock/mediasource/MockBox.cpp +++ b/Source/WebCore/platform/mock/mediasource/MockBox.cpp @@ -31,6 +31,7 @@ #include #include #include +#include #include #include diff --git a/Source/WebCore/rendering/RenderBlock.cpp b/Source/WebCore/rendering/RenderBlock.cpp index bf1a78a7f..b2d056f94 100644 --- a/Source/WebCore/rendering/RenderBlock.cpp +++ b/Source/WebCore/rendering/RenderBlock.cpp @@ -2751,7 +2751,9 @@ void RenderBlock::computePreferredLogicalWidths() { ASSERT(preferredLogicalWidthsDirty()); - updateFirstLetter(); + // FIXME: Do not even try to reshuffle first letter renderers when we are not in layout + // until after webkit.org/b/163848 is fixed. + updateFirstLetter(view().frameView().isInRenderTreeLayout() ? RenderTreeMutationIsAllowed::Yes : RenderTreeMutationIsAllowed::No); m_minPreferredLogicalWidth = 0; m_maxPreferredLogicalWidth = 0; @@ -3301,7 +3303,7 @@ void RenderBlock::getFirstLetter(RenderObject*& firstLetter, RenderElement*& fir firstLetterContainer = nullptr; } -void RenderBlock::updateFirstLetter() +void RenderBlock::updateFirstLetter(RenderTreeMutationIsAllowed mutationAllowedOrNot) { RenderObject* firstLetterObj; RenderElement* firstLetterContainer; @@ -3322,6 +3324,8 @@ void RenderBlock::updateFirstLetter() if (!is(*firstLetterObj)) return; + if (mutationAllowedOrNot != RenderTreeMutationIsAllowed::Yes) + return; // Our layout state is not valid for the repaints we are going to trigger by // adding and removing children of firstLetterContainer. LayoutStateDisabler layoutStateDisabler(view()); diff --git a/Source/WebCore/rendering/RenderBlock.h b/Source/WebCore/rendering/RenderBlock.h index 49468c586..b8292b138 100644 --- a/Source/WebCore/rendering/RenderBlock.h +++ b/Source/WebCore/rendering/RenderBlock.h @@ -243,7 +243,8 @@ public: LayoutUnit collapsedMarginBeforeForChild(const RenderBox& child) const; LayoutUnit collapsedMarginAfterForChild(const RenderBox& child) const; - virtual void updateFirstLetter(); + enum class RenderTreeMutationIsAllowed { Yes, No }; + virtual void updateFirstLetter(RenderTreeMutationIsAllowed = RenderTreeMutationIsAllowed::Yes); void getFirstLetter(RenderObject*& firstLetter, RenderElement*& firstLetterContainer, RenderObject* skipObject = nullptr); virtual void scrollbarsChanged(bool /*horizontalScrollbarChanged*/, bool /*verticalScrollbarChanged*/) { } diff --git a/Source/WebCore/rendering/RenderBox.cpp b/Source/WebCore/rendering/RenderBox.cpp index e4809d288..2fe6cbfa8 100644 --- a/Source/WebCore/rendering/RenderBox.cpp +++ b/Source/WebCore/rendering/RenderBox.cpp @@ -55,6 +55,7 @@ #include "RenderIterator.h" #include "RenderLayer.h" #include "RenderLayerCompositor.h" +#include "RenderMultiColumnFlowThread.h" #include "RenderNamedFlowFragment.h" #include "RenderNamedFlowThread.h" #include "RenderTableCell.h" @@ -2264,6 +2265,21 @@ LayoutRect RenderBox::computeRectForRepaint(const LayoutRect& rect, const Render adjustedRect.expand(locationOffset - flooredLocationOffset); locationOffset = flooredLocationOffset; } + + if (is(this)) { + // We won't normally run this code. Only when the repaintContainer is null (i.e., we're trying + // to get the rect in view coordinates) will we come in here, since normally repaintContainer + // will be set and we'll stop at the flow thread. This case is mainly hit by the check for whether + // or not images should animate. + // FIXME: Just as with offsetFromContainer, we aren't really handling objects that span + // multiple columns properly. + LayoutPoint physicalPoint(flipForWritingMode(adjustedRect.location())); + if (auto* region = downcast(*this).physicalTranslationFromFlowToRegion((physicalPoint))) { + adjustedRect.setLocation(region->flipForWritingMode(physicalPoint)); + return region->computeRectForRepaint(adjustedRect, repaintContainer, fixed); + } + } + LayoutPoint topLeft = adjustedRect.location(); topLeft.move(locationOffset); @@ -3107,17 +3123,22 @@ LayoutUnit RenderBox::computeReplacedLogicalHeightUsing(SizeType heightType, Len case Percent: case Calculated: { - auto cb = isOutOfFlowPositioned() ? container() : containingBlock(); - while (cb && cb->isAnonymous() && !is(*cb)) { - cb = cb->containingBlock(); - downcast(*cb).addPercentHeightDescendant(const_cast(*this)); + auto* container = isOutOfFlowPositioned() ? this->container() : containingBlock(); + while (container && container->isAnonymous()) { + // Stop at rendering context root. + if (is(*container) || is(*container)) + break; + container = container->containingBlock(); + downcast(*container).addPercentHeightDescendant(const_cast(*this)); } // FIXME: This calculation is not patched for block-flow yet. // https://bugs.webkit.org/show_bug.cgi?id=46500 - if (cb->isOutOfFlowPositioned() && cb->style().height().isAuto() && !(cb->style().top().isAuto() || cb->style().bottom().isAuto())) { - ASSERT_WITH_SECURITY_IMPLICATION(cb->isRenderBlock()); - RenderBlock& block = downcast(*cb); + if (container->isOutOfFlowPositioned() + && container->style().height().isAuto() + && !(container->style().top().isAuto() || container->style().bottom().isAuto())) { + ASSERT_WITH_SECURITY_IMPLICATION(container->isRenderBlock()); + auto& block = downcast(*container); LogicalExtentComputedValues computedValues; block.computeLogicalHeight(block.logicalHeight(), 0, computedValues); LayoutUnit newContentHeight = computedValues.m_extent - block.borderAndPaddingLogicalHeight() - block.scrollbarLogicalHeight(); @@ -3130,7 +3151,7 @@ LayoutUnit RenderBox::computeReplacedLogicalHeightUsing(SizeType heightType, Len // https://bugs.webkit.org/show_bug.cgi?id=46496 LayoutUnit availableHeight; if (isOutOfFlowPositioned()) - availableHeight = containingBlockLogicalHeightForPositioned(downcast(cb)); + availableHeight = containingBlockLogicalHeightForPositioned(downcast(container)); else { availableHeight = containingBlockLogicalHeightForContent(IncludeMarginBorderPadding); // It is necessary to use the border-box to match WinIE's broken @@ -3138,15 +3159,16 @@ LayoutUnit RenderBox::computeReplacedLogicalHeightUsing(SizeType heightType, Len // table cells using percentage heights. // FIXME: This needs to be made block-flow-aware. If the cell and image are perpendicular block-flows, this isn't right. // https://bugs.webkit.org/show_bug.cgi?id=46997 - while (cb && !is(*cb) && (cb->style().logicalHeight().isAuto() || cb->style().logicalHeight().isPercentOrCalculated())) { - if (cb->isTableCell()) { + while (container && !is(*container) + && (container->style().logicalHeight().isAuto() || container->style().logicalHeight().isPercentOrCalculated())) { + if (container->isTableCell()) { // Don't let table cells squeeze percent-height replaced elements // availableHeight = std::max(availableHeight, intrinsicLogicalHeight()); return valueForLength(logicalHeight, availableHeight - borderAndPaddingLogicalHeight()); } - downcast(*cb).addPercentHeightDescendant(const_cast(*this)); - cb = cb->containingBlock(); + downcast(*container).addPercentHeightDescendant(const_cast(*this)); + container = container->containingBlock(); } } return adjustContentBoxLogicalHeightForBoxSizing(valueForLength(logicalHeight, availableHeight)); diff --git a/Source/WebCore/rendering/RenderListItem.cpp b/Source/WebCore/rendering/RenderListItem.cpp index 9ce483c2b..06e75c28d 100644 --- a/Source/WebCore/rendering/RenderListItem.cpp +++ b/Source/WebCore/rendering/RenderListItem.cpp @@ -273,7 +273,7 @@ void RenderListItem::insertOrMoveMarkerRendererIfNeeded() if (!m_marker) return; - // FIXME: Do not even try reposition the marker when we are not in layout + // FIXME: Do not even try to reposition the marker when we are not in layout // until after we fixed webkit.org/b/163789. if (!view().frameView().isInRenderTreeLayout()) return; diff --git a/Source/WebCore/rendering/RenderRubyRun.cpp b/Source/WebCore/rendering/RenderRubyRun.cpp index 8abbf9549..3d614add1 100644 --- a/Source/WebCore/rendering/RenderRubyRun.cpp +++ b/Source/WebCore/rendering/RenderRubyRun.cpp @@ -106,7 +106,7 @@ RenderBlock* RenderRubyRun::firstLineBlock() const return 0; } -void RenderRubyRun::updateFirstLetter() +void RenderRubyRun::updateFirstLetter(RenderTreeMutationIsAllowed) { } diff --git a/Source/WebCore/rendering/RenderRubyRun.h b/Source/WebCore/rendering/RenderRubyRun.h index 65cf224a5..3e59ac5db 100644 --- a/Source/WebCore/rendering/RenderRubyRun.h +++ b/Source/WebCore/rendering/RenderRubyRun.h @@ -60,8 +60,8 @@ public: virtual void addChild(RenderObject* child, RenderObject* beforeChild = 0) override; virtual void removeChild(RenderObject&) override; - virtual RenderBlock* firstLineBlock() const override; - virtual void updateFirstLetter() override; + RenderBlock* firstLineBlock() const override; + void updateFirstLetter(RenderTreeMutationIsAllowed = RenderTreeMutationIsAllowed::Yes) override; void getOverhang(bool firstLine, RenderObject* startRenderer, RenderObject* endRenderer, float& startOverhang, float& endOverhang) const; diff --git a/Source/WebCore/rendering/RenderTable.cpp b/Source/WebCore/rendering/RenderTable.cpp index b3be2de98..4f325dfb9 100644 --- a/Source/WebCore/rendering/RenderTable.cpp +++ b/Source/WebCore/rendering/RenderTable.cpp @@ -1456,7 +1456,7 @@ RenderBlock* RenderTable::firstLineBlock() const return nullptr; } -void RenderTable::updateFirstLetter() +void RenderTable::updateFirstLetter(RenderTreeMutationIsAllowed) { } diff --git a/Source/WebCore/rendering/RenderTable.h b/Source/WebCore/rendering/RenderTable.h index e2b585146..f49592569 100644 --- a/Source/WebCore/rendering/RenderTable.h +++ b/Source/WebCore/rendering/RenderTable.h @@ -303,8 +303,8 @@ private: void invalidateCachedColumnOffsets(); - virtual RenderBlock* firstLineBlock() const override final; - virtual void updateFirstLetter() override final; + RenderBlock* firstLineBlock() const final; + void updateFirstLetter(RenderTreeMutationIsAllowed = RenderTreeMutationIsAllowed::Yes) final; virtual void updateLogicalWidth() override final; diff --git a/Source/WebCore/rendering/RenderView.cpp b/Source/WebCore/rendering/RenderView.cpp index 3c10cb5cf..5c374092c 100644 --- a/Source/WebCore/rendering/RenderView.cpp +++ b/Source/WebCore/rendering/RenderView.cpp @@ -52,6 +52,7 @@ #include "StyleInheritedData.h" #include "TransformState.h" #include +#include namespace WebCore { @@ -195,6 +196,10 @@ bool RenderView::hitTest(const HitTestRequest& request, HitTestResult& result) bool RenderView::hitTest(const HitTestRequest& request, const HitTestLocation& location, HitTestResult& result) { document().updateLayout(); + +#if !ASSERT_DISABLED + TemporaryChange hitTestRestorer { m_inHitTesting, true }; +#endif FrameFlatteningLayoutDisallower disallower(frameView()); diff --git a/Source/WebCore/rendering/RenderView.h b/Source/WebCore/rendering/RenderView.h index 40aa58229..9279b9eec 100644 --- a/Source/WebCore/rendering/RenderView.h +++ b/Source/WebCore/rendering/RenderView.h @@ -1,6 +1,6 @@ /* * Copyright (C) 1999 Lars Knoll (knoll@kde.org) - * Copyright (C) 2006, 2015 Apple Inc. + * Copyright (C) 2006, 2015-2016 Apple Inc. * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public @@ -252,6 +252,10 @@ public: const HashSet& boxesWithScrollSnapCoordinates() { return m_boxesWithScrollSnapCoordinates; } #endif +#if !ASSERT_DISABLED + bool inHitTesting() const { return m_inHitTesting; } +#endif + protected: virtual void mapLocalToContainer(const RenderLayerModelObject* repaintContainer, TransformState&, MapCoordinatesFlags, bool* wasFixed) const override; virtual const RenderObject* pushMappingToContainer(const RenderLayerModelObject* ancestorToStopAt, RenderGeometryMap&) const override; @@ -369,6 +373,9 @@ private: bool m_hasSoftwareFilters; bool m_usesFirstLineRules { false }; bool m_usesFirstLetterRules { false }; +#if !ASSERT_DISABLED + bool m_inHitTesting { false }; +#endif HashSet m_renderersWithPausedImageAnimation; HashSet m_visibleInViewportRenderers; diff --git a/Source/WebCore/rendering/svg/RenderSVGText.cpp b/Source/WebCore/rendering/svg/RenderSVGText.cpp index 86063acb4..4bb8ef4bf 100644 --- a/Source/WebCore/rendering/svg/RenderSVGText.cpp +++ b/Source/WebCore/rendering/svg/RenderSVGText.cpp @@ -547,7 +547,7 @@ RenderBlock* RenderSVGText::firstLineBlock() const // Fix for . We should not render :first-letter CSS Style // in a SVG text element context. -void RenderSVGText::updateFirstLetter() +void RenderSVGText::updateFirstLetter(RenderTreeMutationIsAllowed) { } diff --git a/Source/WebCore/rendering/svg/RenderSVGText.h b/Source/WebCore/rendering/svg/RenderSVGText.h index 71be1cde3..b2271954b 100644 --- a/Source/WebCore/rendering/svg/RenderSVGText.h +++ b/Source/WebCore/rendering/svg/RenderSVGText.h @@ -91,8 +91,8 @@ private: virtual AffineTransform localTransform() const override { return m_localTransform; } virtual std::unique_ptr createRootInlineBox() override; - virtual RenderBlock* firstLineBlock() const override; - virtual void updateFirstLetter() override; + RenderBlock* firstLineBlock() const override; + void updateFirstLetter(RenderTreeMutationIsAllowed = RenderTreeMutationIsAllowed::Yes) override; bool shouldHandleSubtreeMutations() const; diff --git a/Source/WebCore/style/StyleTreeResolver.cpp b/Source/WebCore/style/StyleTreeResolver.cpp index d6be6658c..8ab152277 100644 --- a/Source/WebCore/style/StyleTreeResolver.cpp +++ b/Source/WebCore/style/StyleTreeResolver.cpp @@ -49,6 +49,7 @@ #include "RenderWidget.h" #include "Settings.h" #include "ShadowRoot.h" +#include "StyleFontSizeFunctions.h" #include "StyleResolver.h" #include "Text.h" @@ -105,6 +106,15 @@ static void ensurePlaceholderStyle(Document& document) return; placeholderStyle = &RenderStyle::create().leakRef(); placeholderStyle->setDisplay(NONE); + + FontCascadeDescription fontDescription; + fontDescription.setOneFamily(standardFamily); + fontDescription.setKeywordSizeFromIdentifier(CSSValueMedium); + float size = Style::fontSizeForKeyword(CSSValueMedium, false, document); + fontDescription.setSpecifiedSize(size); + fontDescription.setComputedSize(size); + placeholderStyle->setFontDescription(fontDescription); + placeholderStyle->fontCascade().update(&document.fontSelector()); } diff --git a/Source/WebKit/qt/declarative/CMakeLists.txt b/Source/WebKit/qt/declarative/CMakeLists.txt index 6a76e88b5..e1ba22bc1 100644 --- a/Source/WebKit/qt/declarative/CMakeLists.txt +++ b/Source/WebKit/qt/declarative/CMakeLists.txt @@ -38,6 +38,8 @@ set_target_properties(qmlwebkitplugin PROPERTIES ARCHIVE_OUTPUT_DIRECTORY_RELEASE ${qmlwebkit_output_dir} LIBRARY_OUTPUT_DIRECTORY_RELEASE ${qmlwebkit_output_dir} RUNTIME_OUTPUT_DIRECTORY_RELEASE ${qmlwebkit_output_dir} + + AUTOMOC ON ) add_custom_target( diff --git a/Source/WebKit/qt/declarative/experimental/CMakeLists.txt b/Source/WebKit/qt/declarative/experimental/CMakeLists.txt index e4d41798c..1526e6f47 100644 --- a/Source/WebKit/qt/declarative/experimental/CMakeLists.txt +++ b/Source/WebKit/qt/declarative/experimental/CMakeLists.txt @@ -15,6 +15,8 @@ set_target_properties(qmlwebkitexperimentalplugin PROPERTIES ARCHIVE_OUTPUT_DIRECTORY_RELEASE ${qmlwebkitexperimental_output_dir} LIBRARY_OUTPUT_DIRECTORY_RELEASE ${qmlwebkitexperimental_output_dir} RUNTIME_OUTPUT_DIRECTORY_RELEASE ${qmlwebkitexperimental_output_dir} + + AUTOMOC ON ) add_custom_target( diff --git a/Source/WebKit/qt/tests/CMakeLists.txt b/Source/WebKit/qt/tests/CMakeLists.txt index 4fd45c624..3dc6af1d5 100644 --- a/Source/WebKit/qt/tests/CMakeLists.txt +++ b/Source/WebKit/qt/tests/CMakeLists.txt @@ -57,7 +57,7 @@ foreach (testName ${QtWK1ApiTests}) add_executable(tst_${testName} ${tst_${testName}_SOURCES}) target_include_directories(tst_${testName} PRIVATE ${testName}) target_link_libraries(tst_${testName} ${QtWK1ApiTests_LIBRARIES}) - set_target_properties(tst_${testName} PROPERTIES RUNTIME_OUTPUT_DIRECTORY ${QtWK1ApiTests_RUNTIME_OUTPUT_DIRECTORY}) + set_target_properties(tst_${testName} PROPERTIES RUNTIME_OUTPUT_DIRECTORY ${QtWK1ApiTests_RUNTIME_OUTPUT_DIRECTORY} AUTOMOC ON) add_test(${testName} "${QtWK1ApiTests_RUNTIME_OUTPUT_DIRECTORY}/tst_${testName}") set_tests_properties(${testName} PROPERTIES TIMEOUT 60) diff --git a/Source/WebKit/win/Plugins/PluginDatabaseWin.cpp b/Source/WebKit/win/Plugins/PluginDatabaseWin.cpp index ea272601b..8230a793c 100644 --- a/Source/WebKit/win/Plugins/PluginDatabaseWin.cpp +++ b/Source/WebKit/win/Plugins/PluginDatabaseWin.cpp @@ -32,6 +32,7 @@ #include "URL.h" #include "PluginPackage.h" #include +#include namespace WebCore { @@ -62,7 +63,7 @@ static inline void addPluginPathsFromRegistry(HKEY rootKey, HashSet& pat if (result != ERROR_SUCCESS || type != REG_SZ) continue; - paths.add(String(pathStr, pathStrSize / sizeof(WCHAR) - 1)); + paths.add(wcharToString(pathStr, pathStrSize / sizeof(WCHAR) - 1)); } RegCloseKey(key); @@ -83,7 +84,7 @@ void PluginDatabase::getPluginPathsInDirectories(HashSet& paths) const for (Vector::const_iterator it = m_pluginDirectories.begin(); it != end; ++it) { String pattern = *it + "\\*"; - hFind = FindFirstFileW(pattern.charactersWithNullTermination().data(), &findFileData); + hFind = FindFirstFileW(stringToNullTerminatedWChar(pattern).data(), &findFileData); if (hFind == INVALID_HANDLE_VALUE) continue; @@ -92,7 +93,7 @@ void PluginDatabase::getPluginPathsInDirectories(HashSet& paths) const if (findFileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) continue; - String filename = String(findFileData.cFileName, wcslen(findFileData.cFileName)); + String filename = wcharToString(findFileData.cFileName, wcslen(findFileData.cFileName)); if ((!filename.startsWith("np", false) || !filename.endsWith("dll", false)) && (!equalLettersIgnoringASCIICase(filename, "plugin.dll") || !it->endsWith("Shockwave 10", false))) continue; @@ -179,11 +180,11 @@ static inline void addMozillaPluginDirectories(Vector& directories) if (result != ERROR_SUCCESS) break; - String extensionsPath = String(name, nameLen) + "\\Extensions"; + String extensionsPath = wcharToString(name, nameLen) + "\\Extensions"; HKEY extensionsKey; // Try opening the key - result = RegOpenKeyEx(key, extensionsPath.charactersWithNullTermination().data(), 0, KEY_READ, &extensionsKey); + result = RegOpenKeyEx(key, stringToNullTerminatedWChar(extensionsPath).data(), 0, KEY_READ, &extensionsKey); if (result == ERROR_SUCCESS) { // Now get the plugins directory @@ -194,7 +195,7 @@ static inline void addMozillaPluginDirectories(Vector& directories) result = RegQueryValueEx(extensionsKey, TEXT("Plugins"), 0, &type, (LPBYTE)&pluginsDirectoryStr, &pluginsDirectorySize); if (result == ERROR_SUCCESS && type == REG_SZ) - directories.append(String(pluginsDirectoryStr, pluginsDirectorySize / sizeof(WCHAR) - 1)); + directories.append(wcharToString(pluginsDirectoryStr, pluginsDirectorySize / sizeof(WCHAR) - 1)); RegCloseKey(extensionsKey); } @@ -211,7 +212,7 @@ static inline void addWindowsMediaPlayerPluginDirectory(Vector& director DWORD pluginDirectorySize = ::ExpandEnvironmentStringsW(TEXT("%SYSTEMDRIVE%\\PFiles\\Plugins"), pluginDirectoryStr, WTF_ARRAY_LENGTH(pluginDirectoryStr)); if (pluginDirectorySize > 0 && pluginDirectorySize <= WTF_ARRAY_LENGTH(pluginDirectoryStr)) - directories.append(String(pluginDirectoryStr, pluginDirectorySize - 1)); + directories.append(wcharToString(pluginDirectoryStr, pluginDirectorySize - 1)); DWORD type; WCHAR installationDirectoryStr[_MAX_PATH]; @@ -220,7 +221,7 @@ static inline void addWindowsMediaPlayerPluginDirectory(Vector& director HRESULT result = getRegistryValue(HKEY_LOCAL_MACHINE, L"Software\\Microsoft\\MediaPlayer", L"Installation Directory", &type, &installationDirectoryStr, &installationDirectorySize); if (result == ERROR_SUCCESS && type == REG_SZ) - directories.append(String(installationDirectoryStr, installationDirectorySize / sizeof(WCHAR) - 1)); + directories.append(wcharToString(installationDirectoryStr, installationDirectorySize / sizeof(WCHAR) - 1)); } static inline void addAdobeAcrobatPluginDirectory(Vector& directories) @@ -244,10 +245,10 @@ static inline void addAdobeAcrobatPluginDirectory(Vector& directories) if (result != ERROR_SUCCESS) break; - Vector acrobatVersion = parseVersionString(String(name, nameLen)); + Vector acrobatVersion = parseVersionString(wcharToString(name, nameLen)); if (compareVersions(acrobatVersion, latestAcrobatVersion)) { latestAcrobatVersion = acrobatVersion; - latestAcrobatVersionString = String(name, nameLen); + latestAcrobatVersionString = wcharToString(name, nameLen); } } @@ -257,10 +258,10 @@ static inline void addAdobeAcrobatPluginDirectory(Vector& directories) DWORD acrobatInstallPathSize = sizeof(acrobatInstallPathStr); String acrobatPluginKeyPath = "Software\\Adobe\\Acrobat Reader\\" + latestAcrobatVersionString + "\\InstallPath"; - result = getRegistryValue(HKEY_LOCAL_MACHINE, acrobatPluginKeyPath.charactersWithNullTermination().data(), 0, &type, acrobatInstallPathStr, &acrobatInstallPathSize); + result = getRegistryValue(HKEY_LOCAL_MACHINE, stringToNullTerminatedWChar(acrobatPluginKeyPath).data(), 0, &type, acrobatInstallPathStr, &acrobatInstallPathSize); if (result == ERROR_SUCCESS) { - String acrobatPluginDirectory = String(acrobatInstallPathStr, acrobatInstallPathSize / sizeof(WCHAR) - 1) + "\\browser"; + String acrobatPluginDirectory = wcharToString(acrobatInstallPathStr, acrobatInstallPathSize / sizeof(WCHAR) - 1) + "\\browser"; directories.append(acrobatPluginDirectory); } } @@ -289,10 +290,10 @@ static inline void addJavaPluginDirectory(Vector& directories) if (result != ERROR_SUCCESS) break; - Vector javaVersion = parseVersionString(String(name, nameLen)); + Vector javaVersion = parseVersionString(wcharToString(name, nameLen)); if (compareVersions(javaVersion, latestJavaVersion)) { latestJavaVersion = javaVersion; - latestJavaVersionString = String(name, nameLen); + latestJavaVersionString = wcharToString(name, nameLen); } } @@ -304,12 +305,12 @@ static inline void addJavaPluginDirectory(Vector& directories) DWORD useNewPluginSize; String javaPluginKeyPath = "Software\\JavaSoft\\Java Plug-in\\" + latestJavaVersionString; - result = getRegistryValue(HKEY_LOCAL_MACHINE, javaPluginKeyPath.charactersWithNullTermination().data(), L"UseNewJavaPlugin", &type, &useNewPluginValue, &useNewPluginSize); + result = getRegistryValue(HKEY_LOCAL_MACHINE, stringToNullTerminatedWChar(javaPluginKeyPath).data(), L"UseNewJavaPlugin", &type, &useNewPluginValue, &useNewPluginSize); if (result == ERROR_SUCCESS && useNewPluginValue == 1) { - result = getRegistryValue(HKEY_LOCAL_MACHINE, javaPluginKeyPath.charactersWithNullTermination().data(), L"JavaHome", &type, javaInstallPathStr, &javaInstallPathSize); + result = getRegistryValue(HKEY_LOCAL_MACHINE, stringToNullTerminatedWChar(javaPluginKeyPath).data(), L"JavaHome", &type, javaInstallPathStr, &javaInstallPathSize); if (result == ERROR_SUCCESS) { - String javaPluginDirectory = String(javaInstallPathStr, javaInstallPathSize / sizeof(WCHAR) - 1) + "\\bin\\new_plugin"; + String javaPluginDirectory = wcharToString(javaInstallPathStr, javaInstallPathSize / sizeof(WCHAR) - 1) + "\\bin\\new_plugin"; directories.append(javaPluginDirectory); } } @@ -335,7 +336,7 @@ static inline String safariPluginsDirectory() if (!PathRemoveFileSpec(moduleFileNameStr)) goto exit; - pluginsDirectory = String(moduleFileNameStr) + "\\Plugins"; + pluginsDirectory = nullTerminatedWCharToString(moduleFileNameStr) + "\\Plugins"; } exit: return pluginsDirectory; @@ -351,10 +352,10 @@ static inline void addMacromediaPluginDirectories(Vector& directories) WCHAR macromediaDirectoryStr[MAX_PATH]; PathCombine(macromediaDirectoryStr, systemDirectoryStr, TEXT("macromed\\Flash")); - directories.append(macromediaDirectoryStr); + directories.append(nullTerminatedWCharToString(macromediaDirectoryStr)); PathCombine(macromediaDirectoryStr, systemDirectoryStr, TEXT("macromed\\Shockwave 10")); - directories.append(macromediaDirectoryStr); + directories.append(nullTerminatedWCharToString(macromediaDirectoryStr)); } #if PLATFORM(QT) diff --git a/Source/WebKit/win/Plugins/PluginPackageWin.cpp b/Source/WebKit/win/Plugins/PluginPackageWin.cpp index 7119d8854..e0094b96b 100644 --- a/Source/WebKit/win/Plugins/PluginPackageWin.cpp +++ b/Source/WebKit/win/Plugins/PluginPackageWin.cpp @@ -34,10 +34,11 @@ #include "PluginDebug.h" #include "Timer.h" #include "npruntime_impl.h" +#include #include #include #include -#include +#include namespace WebCore { @@ -47,7 +48,7 @@ static String getVersionInfo(const LPVOID versionInfoData, const String& info) UINT bufferLength; String subInfo = "\\StringfileInfo\\040904E4\\" + info; bool retval = VerQueryValueW(versionInfoData, - const_cast(subInfo.charactersWithNullTermination().data()), + stringToNullTerminatedWChar(subInfo).data(), &buffer, &bufferLength); if (!retval || bufferLength == 0) return String(); @@ -167,14 +168,13 @@ void PluginPackage::determineQuirks(const String& mimeType) bool PluginPackage::fetchInfo() { DWORD versionInfoSize, zeroHandle; - versionInfoSize = GetFileVersionInfoSizeW(const_cast(m_path.charactersWithNullTermination().data()), &zeroHandle); + versionInfoSize = GetFileVersionInfoSizeW(stringToNullTerminatedWChar(m_path).data(), &zeroHandle); if (versionInfoSize == 0) return false; auto versionInfoData = std::make_unique(versionInfoSize); - if (!GetFileVersionInfoW(const_cast(m_path.charactersWithNullTermination().data()), - 0, versionInfoSize, versionInfoData.get())) + if (!GetFileVersionInfoW(stringToNullTerminatedWChar(m_path).data(), 0, versionInfoSize, versionInfoData.get())) return false; m_name = getVersionInfo(versionInfoData.get(), "ProductName"); @@ -244,11 +244,11 @@ bool PluginPackage::load() String path = m_path.substring(0, m_path.reverseFind('\\')); - if (!::SetCurrentDirectoryW(path.charactersWithNullTermination().data())) + if (!::SetCurrentDirectoryW(stringToNullTerminatedWChar(path).data())) return false; // Load the library - m_module = ::LoadLibraryExW(m_path.charactersWithNullTermination().data(), 0, LOAD_WITH_ALTERED_SEARCH_PATH); + m_module = ::LoadLibraryExW(stringToNullTerminatedWChar(m_path).data(), 0, LOAD_WITH_ALTERED_SEARCH_PATH); if (!::SetCurrentDirectoryW(currentPath)) { if (m_module) diff --git a/Source/WebKit/win/Plugins/PluginViewWin.cpp b/Source/WebKit/win/Plugins/PluginViewWin.cpp index 68af391fc..a0b41113e 100644 --- a/Source/WebKit/win/Plugins/PluginViewWin.cpp +++ b/Source/WebKit/win/Plugins/PluginViewWin.cpp @@ -71,6 +71,7 @@ #include #include #include +#include #include #if USE(CAIRO) @@ -852,13 +853,13 @@ NPError PluginView::handlePostReadFile(Vector& buffer, uint32_t len, const // Get file info WIN32_FILE_ATTRIBUTE_DATA attrs; - if (GetFileAttributesExW(filename.charactersWithNullTermination().data(), GetFileExInfoStandard, &attrs) == 0) + if (!GetFileAttributesExW(stringToNullTerminatedWChar(filename).data(), GetFileExInfoStandard, &attrs)) return NPERR_FILE_NOT_FOUND; if (attrs.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) return NPERR_FILE_NOT_FOUND; - HANDLE fileHandle = CreateFileW(filename.charactersWithNullTermination().data(), FILE_READ_DATA, FILE_SHARE_READ, 0, OPEN_EXISTING, 0, 0); + HANDLE fileHandle = CreateFileW(stringToNullTerminatedWChar(filename).data(), FILE_READ_DATA, FILE_SHARE_READ, 0, OPEN_EXISTING, 0, 0); if (fileHandle == INVALID_HANDLE_VALUE) return NPERR_FILE_NOT_FOUND; diff --git a/Source/WebKit2/Platform/IPC/unix/ConnectionUnix.cpp b/Source/WebKit2/Platform/IPC/unix/ConnectionUnix.cpp index 18d02cdd9..3902003f9 100644 --- a/Source/WebKit2/Platform/IPC/unix/ConnectionUnix.cpp +++ b/Source/WebKit2/Platform/IPC/unix/ConnectionUnix.cpp @@ -199,6 +199,11 @@ bool Connection::processMessage() memcpy(&messageInfo, messageData, sizeof(messageInfo)); messageData += sizeof(messageInfo); + if (messageInfo.attachmentCount() > attachmentMaxAmount || (!messageInfo.isMessageBodyIsOutOfLine() && messageInfo.bodySize() > messageMaxSize)) { + ASSERT_NOT_REACHED(); + return false; + } + size_t messageLength = sizeof(MessageInfo) + messageInfo.attachmentCount() * sizeof(AttachmentInfo) + (messageInfo.isMessageBodyIsOutOfLine() ? 0 : messageInfo.bodySize()); if (m_readBuffer.size() < messageLength) return false; @@ -256,7 +261,7 @@ bool Connection::processMessage() if (messageInfo.isMessageBodyIsOutOfLine()) { ASSERT(messageInfo.bodySize()); - if (attachmentInfo[attachmentCount].isNull()) { + if (attachmentInfo[attachmentCount].isNull() || attachmentInfo[attachmentCount].getSize() != messageInfo.bodySize()) { ASSERT_NOT_REACHED(); return false; } @@ -334,6 +339,10 @@ static ssize_t readBytesFromSocket(int socketDescriptor, Vector& buffer struct cmsghdr* controlMessage; for (controlMessage = CMSG_FIRSTHDR(&message); controlMessage; controlMessage = CMSG_NXTHDR(&message, controlMessage)) { if (controlMessage->cmsg_level == SOL_SOCKET && controlMessage->cmsg_type == SCM_RIGHTS) { + if (controlMessage->cmsg_len < CMSG_LEN(0) || controlMessage->cmsg_len > attachmentMaxAmount) { + ASSERT_NOT_REACHED(); + break; + } size_t previousFileDescriptorsSize = fileDescriptors.size(); size_t fileDescriptorsCount = (controlMessage->cmsg_len - CMSG_LEN(0)) / sizeof(int); fileDescriptors.grow(fileDescriptors.size() + fileDescriptorsCount); diff --git a/Source/WebKit2/Shared/qt/NativeWebTouchEventQt.cpp b/Source/WebKit2/Shared/qt/NativeWebTouchEventQt.cpp index 5792ef623..f6cc58825 100644 --- a/Source/WebKit2/Shared/qt/NativeWebTouchEventQt.cpp +++ b/Source/WebKit2/Shared/qt/NativeWebTouchEventQt.cpp @@ -26,6 +26,8 @@ #include "config.h" #include "NativeWebTouchEvent.h" +#if ENABLE(TOUCH_EVENTS) + #include "WebEventFactory.h" namespace WebKit { @@ -37,3 +39,5 @@ NativeWebTouchEvent::NativeWebTouchEvent(const QTouchEvent* event, const QTransf } } // namespace WebKit + +#endif // ENABLE(TOUCH_EVENTS) diff --git a/Source/WebKit2/UIProcess/API/qt/tests/CMakeLists.txt b/Source/WebKit2/UIProcess/API/qt/tests/CMakeLists.txt index b26366492..899a9e038 100644 --- a/Source/WebKit2/UIProcess/API/qt/tests/CMakeLists.txt +++ b/Source/WebKit2/UIProcess/API/qt/tests/CMakeLists.txt @@ -87,7 +87,9 @@ set(qmltests_LIBRARIES add_executable(tst_qmltests_WebView ${qmltests_SOURCES}) target_compile_definitions(tst_qmltests_WebView PRIVATE ${tst_qmltests_WebView_DEFINITIONS}) target_link_libraries(tst_qmltests_WebView ${qmltests_LIBRARIES}) +set_target_properties(tst_qmltests_WebView PROPERTIES AUTOMOC ON) add_executable(tst_qmltests_DesktopBehavior ${qmltests_SOURCES}) target_compile_definitions(tst_qmltests_DesktopBehavior PRIVATE ${tst_qmltests_DesktopBehavior_DEFINITIONS}) target_link_libraries(tst_qmltests_DesktopBehavior ${qmltests_LIBRARIES}) +set_target_properties(tst_qmltests_DesktopBehavior PROPERTIES AUTOMOC ON) diff --git a/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp b/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp index b40662f06..d27175cee 100644 --- a/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp +++ b/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp @@ -116,7 +116,7 @@ void WebUserContentControllerProxy::addUserScript(API::UserScript& userScript) void WebUserContentControllerProxy::removeUserScript(const API::UserScript& userScript) { for (WebProcessProxy* process : m_processes) - process->connection()->send(Messages::WebUserContentController::RemoveUserScript({ userScript.userScript().url().string() }), m_identifier); + process->connection()->send(Messages::WebUserContentController::RemoveUserScript(userScript.userScript().url().string()), m_identifier); m_userScripts->elements().removeAll(&userScript); } @@ -140,7 +140,7 @@ void WebUserContentControllerProxy::addUserStyleSheet(API::UserStyleSheet& userS void WebUserContentControllerProxy::removeUserStyleSheet(const API::UserStyleSheet& userStyleSheet) { for (WebProcessProxy* process : m_processes) - process->connection()->send(Messages::WebUserContentController::RemoveUserStyleSheet({ userStyleSheet.userStyleSheet().url().string() }), m_identifier); + process->connection()->send(Messages::WebUserContentController::RemoveUserStyleSheet(userStyleSheet.userStyleSheet().url().string()), m_identifier); m_userStyleSheets->elements().removeAll(&userStyleSheet); } diff --git a/Source/WebKit2/UIProcess/qt/QtPageClient.cpp b/Source/WebKit2/UIProcess/qt/QtPageClient.cpp index c4edb793e..5f62dc600 100644 --- a/Source/WebKit2/UIProcess/qt/QtPageClient.cpp +++ b/Source/WebKit2/UIProcess/qt/QtPageClient.cpp @@ -110,10 +110,12 @@ void QtPageClient::didChangeViewportProperties(const WebCore::ViewportAttributes QQuickWebViewPrivate::get(m_webView)->didChangeViewportProperties(attr); } +#if ENABLE(DRAG_SUPPORT) void QtPageClient::startDrag(const WebCore::DragData& dragData, PassRefPtr dragImage) { m_eventHandler->startDrag(dragData, dragImage); } +#endif void QtPageClient::handleDownloadRequest(DownloadProxy* download) { diff --git a/Source/WebKit2/UIProcess/qt/QtPageClient.h b/Source/WebKit2/UIProcess/qt/QtPageClient.h index 3467ceaa9..b31720bc8 100644 --- a/Source/WebKit2/UIProcess/qt/QtPageClient.h +++ b/Source/WebKit2/UIProcess/qt/QtPageClient.h @@ -73,7 +73,9 @@ public: void updateAcceleratedCompositingMode(const LayerTreeContext&) override; void pageClosed() override { } void preferencesDidChange() override { } +#if ENABLE(DRAG_SUPPORT) void startDrag(const WebCore::DragData&, PassRefPtr dragImage) override; +#endif void setCursor(const WebCore::Cursor&) override; void setCursorHiddenUntilMouseMoves(bool) override; void toolTipChanged(const String&, const String&) override; diff --git a/Source/WebKit2/UIProcess/qt/QtWebPageEventHandler.cpp b/Source/WebKit2/UIProcess/qt/QtWebPageEventHandler.cpp index d05649736..2a7d6f15e 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebPageEventHandler.cpp +++ b/Source/WebKit2/UIProcess/qt/QtWebPageEventHandler.cpp @@ -184,16 +184,21 @@ void QtWebPageEventHandler::handleHoverMoveEvent(QHoverEvent* ev) void QtWebPageEventHandler::handleDragEnterEvent(QDragEnterEvent* ev) { +#if ENABLE(DRAG_SUPPORT) m_webPageProxy->resetCurrentDragInformation(); QTransform fromItemTransform = m_webPage->transformFromItem(); // FIXME: Should not use QCursor::pos() DragData dragData(ev->mimeData(), fromItemTransform.map(ev->pos()), QCursor::pos(), dropActionToDragOperation(ev->possibleActions())); m_webPageProxy->dragEntered(dragData); ev->acceptProposedAction(); +#else + Q_UNUSED(ev); +#endif } void QtWebPageEventHandler::handleDragLeaveEvent(QDragLeaveEvent* ev) { +#if ENABLE(DRAG_SUPPORT) bool accepted = ev->isAccepted(); // FIXME: Should not use QCursor::pos() @@ -202,10 +207,14 @@ void QtWebPageEventHandler::handleDragLeaveEvent(QDragLeaveEvent* ev) m_webPageProxy->resetCurrentDragInformation(); ev->setAccepted(accepted); +#else + Q_UNUSED(ev); +#endif } void QtWebPageEventHandler::handleDragMoveEvent(QDragMoveEvent* ev) { +#if ENABLE(DRAG_SUPPORT) bool accepted = ev->isAccepted(); QTransform fromItemTransform = m_webPage->transformFromItem(); @@ -217,10 +226,14 @@ void QtWebPageEventHandler::handleDragMoveEvent(QDragMoveEvent* ev) ev->accept(); ev->setAccepted(accepted); +#else + Q_UNUSED(ev); +#endif } void QtWebPageEventHandler::handleDropEvent(QDropEvent* ev) { +#if ENABLE(DRAG_SUPPORT) bool accepted = ev->isAccepted(); QTransform fromItemTransform = m_webPage->transformFromItem(); // FIXME: Should not use QCursor::pos() @@ -232,6 +245,9 @@ void QtWebPageEventHandler::handleDropEvent(QDropEvent* ev) ev->accept(); ev->setAccepted(accepted); +#else + Q_UNUSED(ev); +#endif } void QtWebPageEventHandler::activateTapHighlight(const QTouchEvent::TouchPoint& point) @@ -615,6 +631,7 @@ void QtWebPageEventHandler::didFindZoomableArea(const IntPoint& target, const In void QtWebPageEventHandler::startDrag(const WebCore::DragData& dragData, PassRefPtr dragImage) { +#if ENABLE(DRAG_SUPPORT) QImage dragQImage; if (dragImage) dragQImage = dragImage->createQImage(); @@ -639,6 +656,10 @@ void QtWebPageEventHandler::startDrag(const WebCore::DragData& dragData, PassRef } m_webPageProxy->dragEnded(clientPosition, globalPosition, dropActionToDragOperation(actualDropAction)); +#else + Q_UNUSED(dragData); + Q_UNUSED(dragImage); +#endif } } // namespace WebKit diff --git a/Source/WebKit2/WebProcess/InjectedBundle/DOM/InjectedBundleRangeHandle.cpp b/Source/WebKit2/WebProcess/InjectedBundle/DOM/InjectedBundleRangeHandle.cpp index dcb73b3ff..dde8526fb 100644 --- a/Source/WebKit2/WebProcess/InjectedBundle/DOM/InjectedBundleRangeHandle.cpp +++ b/Source/WebKit2/WebProcess/InjectedBundle/DOM/InjectedBundleRangeHandle.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2010, 2015 Apple Inc. All rights reserved. + * Copyright (C) 2010, 2015-2016 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -114,6 +114,8 @@ PassRefPtr InjectedBundleRangeHandle::renderedImage(SnapshotOptions op if (!frameView) return nullptr; + Ref protector(*frame); + VisibleSelection oldSelection = frame->selection().selection(); frame->selection().setSelection(VisibleSelection(*m_range)); diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp b/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp index 380208a46..8b93b2903 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp +++ b/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp @@ -26,6 +26,8 @@ #include "config.h" #include "WebDragClient.h" +#if ENABLE(DRAG_SUPPORT) + #include "DataTransfer.h" #include "DragData.h" #include "GraphicsContext.h" @@ -67,3 +69,5 @@ void WebDragClient::startDrag(DragImageRef dragImage, const IntPoint& clientPosi } } + +#endif // ENABLE(DRAG_SUPPORT) diff --git a/Source/WebKit2/WebProcess/WebPage/WebPage.cpp b/Source/WebKit2/WebProcess/WebPage/WebPage.cpp index c8d54d523..6a69492d9 100644 --- a/Source/WebKit2/WebProcess/WebPage/WebPage.cpp +++ b/Source/WebKit2/WebProcess/WebPage/WebPage.cpp @@ -4493,6 +4493,8 @@ void WebPage::insertTextAsync(const String& text, const EditingRange& replacemen { Frame& frame = m_page->focusController().focusedOrMainFrame(); + Ref protector(frame); + if (replacementEditingRange.location != notFound) { RefPtr replacementRange = rangeFromEditingRange(frame, replacementEditingRange, static_cast(editingRangeIsRelativeTo)); if (replacementRange) @@ -4655,6 +4657,8 @@ void WebPage::setComposition(const String& text, const Vector protector(*targetFrame); + if (replacementLength > 0) { // The layout needs to be uptodate before setting a selection targetFrame->document()->updateLayout(); diff --git a/Source/cmake/OptionsCommon.cmake b/Source/cmake/OptionsCommon.cmake index 4529bdd84..529e2bc0d 100644 --- a/Source/cmake/OptionsCommon.cmake +++ b/Source/cmake/OptionsCommon.cmake @@ -32,6 +32,10 @@ if (COMPILER_IS_GCC_OR_CLANG) set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fno-exceptions -fno-strict-aliasing") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fno-exceptions -fno-strict-aliasing -fno-rtti") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11") + if (NOT (COMPILER_IS_CLANG AND "${CLANG_VERSION}" VERSION_LESS 4.0.0)) + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-expansion-to-defined") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wno-expansion-to-defined") + endif () endif () if (COMPILER_IS_CLANG AND CMAKE_GENERATOR STREQUAL "Ninja") @@ -196,9 +200,9 @@ endif () # The Ninja generator does not yet know how to build archives in pieces, and so response # files must be used to deal with very long linker command lines. -# See https://bugs.webkit.org/show_bug.cgi?id=129771 -# The Apple Toolchain doesn't support response files. -if (NOT APPLE) +# CMake does this automatically, but the condition was wrong on Linux until CMake 3.2. +# See https://cmake.org/Bug/view.php?id=14892 +if ((CMAKE_HOST_SYSTEM_NAME STREQUAL "Linux") AND (CMAKE_VERSION VERSION_LESS 3.2)) set(CMAKE_NINJA_FORCE_RESPONSE_FILE 1) endif () diff --git a/Source/cmake/OptionsQt.cmake b/Source/cmake/OptionsQt.cmake index 6dc423109..1930027d1 100644 --- a/Source/cmake/OptionsQt.cmake +++ b/Source/cmake/OptionsQt.cmake @@ -59,6 +59,40 @@ macro(QT_ADD_EXTRA_WEBKIT_TARGET_EXPORT target) endif () endmacro() +macro(QTWEBKIT_GENERATE_MOC_FILES_CPP) + foreach (_file ${ARGN}) + get_filename_component(_ext ${_file} EXT) + if (NOT _ext STREQUAL ".cpp") + message(FATAL_ERROR "QTWEBKIT_GENERATE_MOC_FILES_CPP must be used for .cpp files only") + endif () + get_filename_component(_name_we ${_file} NAME_WE) + set(_moc_name "${CMAKE_CURRENT_BINARY_DIR}/${_name_we}.moc") + qt5_generate_moc(${_file} ${_moc_name}) + ADD_SOURCE_DEPENDENCIES(${_file} ${_moc_name}) + endforeach () +endmacro() + +macro(QTWEBKIT_GENERATE_MOC_FILE_H _header _source) + get_filename_component(_header_ext ${_header} EXT) + get_filename_component(_source_ext ${_source} EXT) + if ((NOT _header_ext STREQUAL ".h") OR (NOT _source_ext STREQUAL ".cpp")) + message(FATAL_ERROR "QTWEBKIT_GENERATE_MOC_FILE_H must be called with arguments being .h and .cpp files") + endif () + get_filename_component(_name_we ${_header} NAME_WE) + set(_moc_name "${CMAKE_CURRENT_BINARY_DIR}/moc_${_name_we}.cpp") + qt5_generate_moc(${_header} ${_moc_name}) + ADD_SOURCE_DEPENDENCIES(${_source} ${_moc_name}) +endmacro() + +macro(QTWEBKIT_GENERATE_MOC_FILES_H) + foreach (_header ${ARGN}) + get_filename_component(_header_dir ${_header} DIRECTORY) + get_filename_component(_name_we ${_header} NAME_WE) + set(_source "${_header_dir}/${_name_we}.cpp") + QTWEBKIT_GENERATE_MOC_FILE_H(${_header} ${_source}) + endforeach () +endmacro() + set(CMAKE_MACOSX_RPATH ON) add_definitions(-DBUILDING_QT__=1) @@ -98,6 +132,13 @@ else () set(USE_QT_MULTIMEDIA_DEFAULT OFF) endif () +if (MSVC) + set(USE_QT_MULTIMEDIA_DEFAULT OFF) + set(USE_MEDIA_FOUNDATION_DEFAULT ON) +else () + set(USE_MEDIA_FOUNDATION_DEFAULT OFF) +endif () + if (CMAKE_SYSTEM_NAME MATCHES "Linux") set(ENABLE_GAMEPAD_DEPRECATED_DEFAULT ON) else () @@ -130,7 +171,7 @@ endif () # and the option is not relevant to any other WebKit ports. WEBKIT_OPTION_DEFINE(USE_GSTREAMER "Use GStreamer implementation of MediaPlayer" PUBLIC ${USE_GSTREAMER_DEFAULT}) WEBKIT_OPTION_DEFINE(USE_LIBHYPHEN "Use automatic hyphenation with LibHyphen" PUBLIC ${USE_LIBHYPHEN_DEFAULT}) -WEBKIT_OPTION_DEFINE(USE_MEDIA_FOUNDATION "Use MediaFoundation implementation of MediaPlayer" PUBLIC OFF) +WEBKIT_OPTION_DEFINE(USE_MEDIA_FOUNDATION "Use MediaFoundation implementation of MediaPlayer" PUBLIC ${USE_MEDIA_FOUNDATION_DEFAULT}) WEBKIT_OPTION_DEFINE(USE_QT_MULTIMEDIA "Use Qt Multimedia implementation of MediaPlayer" PUBLIC ${USE_QT_MULTIMEDIA_DEFAULT}) WEBKIT_OPTION_DEFINE(USE_WOFF2 "Include support of WOFF2 fonts format" PUBLIC ON) WEBKIT_OPTION_DEFINE(ENABLE_INSPECTOR_UI "Include Inspector UI into resources" PUBLIC ON) @@ -490,8 +531,6 @@ option(USE_LINKER_VERSION_SCRIPT "Use linker script for ABI compatibility with Q # Find includes in corresponding build directories set(CMAKE_INCLUDE_CURRENT_DIR ON) -# Instruct CMake to run moc automatically when needed. -set(CMAKE_AUTOMOC ON) # TODO: figure out if we can run automoc only on Qt sources diff --git a/Source/cmake/WebKitMacros.cmake b/Source/cmake/WebKitMacros.cmake index d1edb210c..858e2e47d 100644 --- a/Source/cmake/WebKitMacros.cmake +++ b/Source/cmake/WebKitMacros.cmake @@ -33,8 +33,12 @@ macro(ADD_PRECOMPILED_HEADER _header _cpp _source) PROPERTIES COMPILE_FLAGS "/Yc\"${_header}\" /Fp\"${PrecompiledBinary}\"" OBJECT_OUTPUTS "${PrecompiledBinary}") set_source_files_properties(${_sources} - PROPERTIES COMPILE_FLAGS "/Yu\"${_header}\" /FI\"${_header}\" /Fp\"${PrecompiledBinary}\"" - OBJECT_DEPENDS "${PrecompiledBinary}") + PROPERTIES COMPILE_FLAGS "/Yu\"${_header}\" /FI\"${_header}\" /Fp\"${PrecompiledBinary}\"") + + foreach (_src ${_sources}) + ADD_SOURCE_DEPENDENCIES(${_src} ${PrecompiledBinary}) + endforeach () + list(APPEND ${_source} ${_cpp}) endif () #FIXME: Add support for Xcode. diff --git a/Tools/DumpRenderTree/CMakeLists.txt b/Tools/DumpRenderTree/CMakeLists.txt index eb7c1f4ff..db6ef4304 100644 --- a/Tools/DumpRenderTree/CMakeLists.txt +++ b/Tools/DumpRenderTree/CMakeLists.txt @@ -127,3 +127,7 @@ endif () if (WIN32) add_dependencies(DumpRenderTree DumpRenderTreeLib) endif () + +if (${PORT} STREQUAL "Qt") + set_target_properties(DumpRenderTree PROPERTIES AUTOMOC ON) +endif () diff --git a/Tools/MiniBrowser/qt/CMakeLists.txt b/Tools/MiniBrowser/qt/CMakeLists.txt index 0d5c7783f..e77d3bd54 100644 --- a/Tools/MiniBrowser/qt/CMakeLists.txt +++ b/Tools/MiniBrowser/qt/CMakeLists.txt @@ -61,4 +61,4 @@ include_directories(${MiniBrowser_INCLUDE_DIRECTORIES}) include_directories(SYSTEM ${MiniBrowser_SYSTEM_INCLUDE_DIRECTORIES}) add_executable(MiniBrowser ${MiniBrowser_SOURCES}) target_link_libraries(MiniBrowser ${MiniBrowser_LIBRARIES}) -set_target_properties(MiniBrowser PROPERTIES FOLDER "Tools") +set_target_properties(MiniBrowser PROPERTIES FOLDER "Tools" AUTOMOC ON) diff --git a/Tools/QtTestBrowser/CMakeLists.txt b/Tools/QtTestBrowser/CMakeLists.txt index f43bb7852..a091c9541 100644 --- a/Tools/QtTestBrowser/CMakeLists.txt +++ b/Tools/QtTestBrowser/CMakeLists.txt @@ -66,7 +66,7 @@ include_directories(${QtTestBrowser_INCLUDE_DIRECTORIES}) include_directories(SYSTEM ${QtTestBrowser_SYSTEM_INCLUDE_DIRECTORIES}) add_executable(QtTestBrowser ${QtTestBrowser_SOURCES}) target_link_libraries(QtTestBrowser ${QtTestBrowser_LIBRARIES}) -set_target_properties(QtTestBrowser PROPERTIES FOLDER "Tools") +set_target_properties(QtTestBrowser PROPERTIES FOLDER "Tools" AUTOMOC ON) if (${CMAKE_BUILD_TYPE} MATCHES "Release") set_target_properties(QtTestBrowser PROPERTIES WIN32_EXECUTABLE ON) diff --git a/Tools/QtTestBrowser/launcherwindow.cpp b/Tools/QtTestBrowser/launcherwindow.cpp index 26b6dce79..0fd64654e 100644 --- a/Tools/QtTestBrowser/launcherwindow.cpp +++ b/Tools/QtTestBrowser/launcherwindow.cpp @@ -353,6 +353,10 @@ void LauncherWindow::createChrome() touchMockAction->setCheckable(true); touchMockAction->setShortcut(QKeySequence(Qt::CTRL | Qt::ALT | Qt::Key_T)); + QAction* toggleWebSecurity = toolsMenu->addAction("Disable Web Security", this, SLOT(toggleWebSecurity(bool))); + toggleWebSecurity->setCheckable(true); + toggleWebSecurity->setChecked(false); + toolsMenu->addSeparator(); QAction* toggleLocalStorage = toolsMenu->addAction("Enable Local Storage", this, SLOT(toggleLocalStorage(bool))); @@ -1001,6 +1005,11 @@ void LauncherWindow::togglePrivateBrowsing(bool enable) page()->settings()->setAttribute(QWebSettings::PrivateBrowsingEnabled, enable); } +void LauncherWindow::toggleWebSecurity(bool enable) +{ + page()->settings()->setAttribute(QWebSettings::WebSecurityEnabled, !enable); +} + void LauncherWindow::setUseDiskCookies(bool enable) { testBrowserCookieJarInstance()->setDiskStorageEnabled(enable); diff --git a/Tools/QtTestBrowser/launcherwindow.h b/Tools/QtTestBrowser/launcherwindow.h index 0b5ea32db..a05a6cd56 100644 --- a/Tools/QtTestBrowser/launcherwindow.h +++ b/Tools/QtTestBrowser/launcherwindow.h @@ -144,6 +144,7 @@ protected Q_SLOTS: void toggleJavascriptCanOpenWindows(bool enable); void toggleAutoLoadImages(bool enable); void togglePrivateBrowsing(bool enable); + void toggleWebSecurity(bool enable); void setUseDiskCookies(bool enable); void clearCookies(); void togglePlugins(bool enable); diff --git a/Tools/qt/jhbuild.modules b/Tools/qt/jhbuild.modules index f59f198df..b3e0c5101 100644 --- a/Tools/qt/jhbuild.modules +++ b/Tools/qt/jhbuild.modules @@ -124,14 +124,17 @@ + autogen-sh="./autogen.sh; ./configure --without-python --without-valid --without-xinclude --without-xptr --without-c14n --without-catalog --without-regexps --without-zlib --without-lzma --without-schemas --without-schematron --without-threads --without-legacy --without-http --without-iconv --with-icu"> + + + - + diff --git a/Tools/qt/manifest.txt b/Tools/qt/manifest.txt index b7aeadcea..6fe3e9546 100644 --- a/Tools/qt/manifest.txt +++ b/Tools/qt/manifest.txt @@ -69,6 +69,7 @@ exclude Source/WebKit2/Resources file Source/WebCore/English.lproj/mediaControlsLocalizedStrings.js # Windows-specific code +file Source/WTF/wtf/text/win file Source/WTF/wtf/threads/win/BinarySemaphoreWin.cpp file Source/WTF/wtf/win file Source/WebCore/platform/graphics/win/LocalWindowsContext.h -- cgit v1.2.3 From d10511e0a3f655ab2b1dfebfd9c17ade151a7cfe Mon Sep 17 00:00:00 2001 From: Konstantin Tokarev Date: Thu, 29 Jun 2017 15:38:30 +0300 Subject: Import WebKit commit 3c9fc2fb47474909f5c30b518d372c854a3ec433 Change-Id: Iccd335ea312d91e826885857fee6d0da3e913b8c Reviewed-by: Konstantin Tokarev --- Source/JavaScriptCore/CMakeLists.txt | 4 +- Source/JavaScriptCore/DerivedSources.make | 4 +- .../assembler/AbstractMacroAssembler.h | 14 + Source/JavaScriptCore/assembler/MIPSAssembler.h | 59 +- .../JavaScriptCore/assembler/MacroAssemblerMIPS.h | 52 +- Source/JavaScriptCore/dfg/DFGFixupPhase.cpp | 2 +- Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp | 58 + .../disassembler/udis86/differences.txt | 15 - Source/JavaScriptCore/disassembler/udis86/itab.py | 360 --- .../JavaScriptCore/disassembler/udis86/optable.xml | 3360 +++++++++++++------- .../JavaScriptCore/disassembler/udis86/ud_itab.py | 379 +++ .../disassembler/udis86/ud_opcode.py | 771 +++-- .../disassembler/udis86/ud_optable.py | 103 - Source/JavaScriptCore/disassembler/udis86/udis86.c | 370 ++- .../disassembler/udis86/udis86_decode.c | 1149 ++++--- .../disassembler/udis86/udis86_decode.h | 253 +- .../disassembler/udis86/udis86_extern.h | 73 +- .../disassembler/udis86/udis86_input.c | 262 -- .../disassembler/udis86/udis86_input.h | 67 - .../disassembler/udis86/udis86_syn-att.c | 312 +- .../disassembler/udis86/udis86_syn-intel.c | 333 +- .../disassembler/udis86/udis86_syn.c | 229 +- .../disassembler/udis86/udis86_syn.h | 26 +- .../disassembler/udis86/udis86_types.h | 312 +- .../disassembler/udis86/udis86_udint.h | 98 + Source/JavaScriptCore/jit/ExecutableAllocator.h | 2 +- Source/WTF/wtf/OSAllocatorPosix.cpp | 37 + Source/WTF/wtf/Platform.h | 12 +- Source/WTF/wtf/StringExtras.h | 41 +- Source/WTF/wtf/qt/WorkQueueQt.cpp | 1 - Source/WebCore/page/FrameView.cpp | 2 +- .../platform/graphics/filters/FEConvolveMatrix.cpp | 4 +- .../WebCore/platform/graphics/qt/FontCacheQt.cpp | 1 - .../WebCore/platform/graphics/qt/FontCascadeQt.cpp | 9 +- .../platform/graphics/qt/FontCustomPlatformData.h | 1 - .../graphics/qt/FontCustomPlatformDataQt.cpp | 1 - .../platform/graphics/qt/FontPlatformData.h | 1 - Source/WebCore/platform/graphics/qt/GradientQt.cpp | 1 - .../platform/graphics/qt/GraphicsContext3DQt.cpp | 3 - .../platform/graphics/qt/GraphicsContextQt.cpp | 2 - Source/WebCore/platform/graphics/qt/IconQt.cpp | 1 - .../platform/graphics/qt/ImageBufferDataQt.cpp | 1 - .../WebCore/platform/graphics/qt/ImageBufferQt.cpp | 2 - .../platform/graphics/qt/MediaPlayerPrivateQt.cpp | 3 - Source/WebCore/platform/graphics/qt/PathQt.cpp | 1 - Source/WebCore/platform/graphics/qt/PatternQt.cpp | 3 +- .../WebCore/platform/graphics/qt/StillImageQt.cpp | 1 - .../graphics/qt/TransformationMatrixQt.cpp | 2 - .../platform/network/qt/ResourceHandleQt.cpp | 4 - .../platform/network/qt/ResourceRequestQt.cpp | 6 + .../WebCore/platform/qt/DeviceMotionClientQt.cpp | 1 - Source/WebCore/platform/qt/GamepadsQt.cpp | 1 - Source/WebCore/platform/qt/MIMETypeRegistryQt.cpp | 1 - .../platform/qt/MainThreadSharedTimerQt.cpp | 1 - Source/WebCore/platform/qt/PlatformGestureEvent.h | 1 - Source/WebCore/platform/qt/PlatformScreenQt.cpp | 1 - Source/WebCore/platform/qt/RenderThemeQStyle.cpp | 6 - Source/WebCore/platform/qt/RenderThemeQt.cpp | 15 +- Source/WebCore/platform/qt/RenderThemeQtMobile.cpp | 3 - .../WebCore/platform/qt/TemporaryLinkStubsQt.cpp | 33 +- Source/WebCore/platform/qt/ThirdPartyCookiesQt.cpp | 2 - Source/WebCore/platform/qt/URLQt.cpp | 2 - Source/WebCore/platform/qt/WidgetQt.cpp | 1 - Source/WebCore/xml/XSLTUnicodeSort.cpp | 16 +- .../xml/parser/XMLDocumentParserLibxml2.cpp | 23 +- Source/WebKit/CMakeLists.txt | 2 +- Source/WebKit/PlatformQt.cmake | 2 +- Source/WebKit2/CMakeLists.txt | 35 +- .../WebKit2/NetworkProcess/qt/NetworkProcessQt.cpp | 1 - .../qt/RemoteNetworkingContextQt.cpp | 1 - Source/WebKit2/Platform/IPC/win/ConnectionWin.cpp | 5 +- .../PluginProcess/qt/PluginControllerProxyQt.cpp | 1 - .../WebKit2/PluginProcess/qt/PluginProcessQt.cpp | 1 - Source/WebKit2/Shared/qt/ArgumentCodersQt.cpp | 1 - Source/WebKit2/Shared/qt/WebEventFactoryQt.cpp | 1 - Source/WebKit2/UIProcess/API/cpp/qt/WKStringQt.cpp | 1 - Source/WebKit2/UIProcess/API/cpp/qt/WKURLQt.cpp | 3 +- .../UIProcess/API/qt/qquicknetworkreply_p.h | 1 - Source/WebKit2/UIProcess/API/qt/qquickwebpage.cpp | 2 - Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp | 2 - .../WebKit2/UIProcess/API/qt/qquickwebview_p_p.h | 1 - .../UIProcess/API/qt/qwebnavigationhistory.cpp | 1 - .../UIProcess/API/qt/qwebnavigationhistory_p_p.h | 1 - .../WebKit2/UIProcess/API/qt/qwebpreferences.cpp | 2 - .../UIProcess/Launcher/qt/ProcessLauncherQt.cpp | 4 - .../qt/PageViewportControllerClientQt.cpp | 1 - Source/WebKit2/UIProcess/qt/QtWebContext.cpp | 1 - Source/WebKit2/UIProcess/qt/QtWebContext.h | 1 - Source/WebKit2/UIProcess/qt/QtWebError.cpp | 3 - .../WebKit2/UIProcess/qt/QtWebPagePolicyClient.cpp | 4 +- Source/WebKit2/UIProcess/qt/QtWebPageUIClient.cpp | 1 - Source/WebKit2/UIProcess/qt/QtWebPageUIClient.h | 2 - .../UIProcess/qt/WebFullScreenManagerProxyQt.cpp | 1 - Source/WebKit2/UIProcess/qt/WebProcessPoolQt.cpp | 1 - .../WebCoreSupport/qt/WebDragClientQt.cpp | 1 - Source/WebKit2/WebProcess/WebPage/qt/WebPageQt.cpp | 2 - Source/WebKit2/WebProcess/qt/QtBuiltinBundle.cpp | 2 - Source/WebKit2/WebProcess/qt/QtBuiltinBundle.h | 1 - .../WebKit2/WebProcess/qt/QtBuiltinBundlePage.cpp | 2 - Source/cmake/ECMEnableSanitizers.cmake | 173 + Source/cmake/OptionsQt.cmake | 34 +- Source/cmake/WebKitCommon.cmake | 3 + Tools/MiniBrowser/qt/icons/find.png | Bin 930 -> 122 bytes Tools/MiniBrowser/qt/icons/plus.png | Bin 1480 -> 360 bytes Tools/MiniBrowser/qt/icons/touch.png | Bin 6803 -> 444 bytes Tools/qmake/projects/run_cmake.pro | 27 +- 106 files changed, 5550 insertions(+), 3692 deletions(-) delete mode 100644 Source/JavaScriptCore/disassembler/udis86/itab.py create mode 100644 Source/JavaScriptCore/disassembler/udis86/ud_itab.py delete mode 100644 Source/JavaScriptCore/disassembler/udis86/ud_optable.py delete mode 100644 Source/JavaScriptCore/disassembler/udis86/udis86_input.c delete mode 100644 Source/JavaScriptCore/disassembler/udis86/udis86_input.h create mode 100644 Source/JavaScriptCore/disassembler/udis86/udis86_udint.h create mode 100644 Source/cmake/ECMEnableSanitizers.cmake diff --git a/Source/JavaScriptCore/CMakeLists.txt b/Source/JavaScriptCore/CMakeLists.txt index 1957446b4..a207c0f60 100644 --- a/Source/JavaScriptCore/CMakeLists.txt +++ b/Source/JavaScriptCore/CMakeLists.txt @@ -388,7 +388,6 @@ set(JavaScriptCore_SOURCES disassembler/udis86/udis86.c disassembler/udis86/udis86_decode.c - disassembler/udis86/udis86_input.c disassembler/udis86/udis86_itab_holder.c disassembler/udis86/udis86_syn-att.c disassembler/udis86/udis86_syn-intel.c @@ -909,14 +908,13 @@ endforeach () set(UDIS_GEN_DEP disassembler/udis86/ud_opcode.py - disassembler/udis86/ud_optable.py ) add_custom_command( OUTPUT ${DERIVED_SOURCES_JAVASCRIPTCORE_DIR}/udis86_itab.c ${DERIVED_SOURCES_JAVASCRIPTCORE_DIR}/udis86_itab.h DEPENDS ${UDIS_GEN_DEP} WORKING_DIRECTORY ${DERIVED_SOURCES_JAVASCRIPTCORE_DIR} - COMMAND ${PYTHON_EXECUTABLE} ${JAVASCRIPTCORE_DIR}/disassembler/udis86/itab.py ${JAVASCRIPTCORE_DIR}/disassembler/udis86/optable.xml + COMMAND ${PYTHON_EXECUTABLE} ${JAVASCRIPTCORE_DIR}/disassembler/udis86/ud_itab.py ${JAVASCRIPTCORE_DIR}/disassembler/udis86/optable.xml ${DERIVED_SOURCES_JAVASCRIPTCORE_DIR} VERBATIM) list(APPEND JavaScriptCore_HEADERS diff --git a/Source/JavaScriptCore/DerivedSources.make b/Source/JavaScriptCore/DerivedSources.make index 883cc34e0..d5a3fc159 100644 --- a/Source/JavaScriptCore/DerivedSources.make +++ b/Source/JavaScriptCore/DerivedSources.make @@ -171,8 +171,8 @@ KeywordLookup.h: KeywordLookupGenerator.py Keywords.table # udis86 instruction tables -udis86_itab.h: $(JavaScriptCore)/disassembler/udis86/itab.py $(JavaScriptCore)/disassembler/udis86/optable.xml - $(PYTHON) $(JavaScriptCore)/disassembler/udis86/itab.py $(JavaScriptCore)/disassembler/udis86/optable.xml +udis86_itab.h: $(JavaScriptCore)/disassembler/udis86/ud_itab.py $(JavaScriptCore)/disassembler/udis86/optable.xml + $(PYTHON) $(JavaScriptCore)/disassembler/udis86/ud_itab.py $(JavaScriptCore)/disassembler/udis86/optable.xml . # Bytecode files diff --git a/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h b/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h index 1e2d295c9..cbea00e30 100644 --- a/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h +++ b/Source/JavaScriptCore/assembler/AbstractMacroAssembler.h @@ -58,6 +58,15 @@ inline bool isARM64() #endif } +inline bool isMIPS() +{ +#if CPU(MIPS) + return true; +#else + return false; +#endif +} + inline bool isX86() { #if CPU(X86_64) || CPU(X86) @@ -86,6 +95,11 @@ inline bool optimizeForARM64() return isARM64() && Options::useArchitectureSpecificOptimizations(); } +inline bool optimizeForMIPS() +{ + return isMIPS() && Options::useArchitectureSpecificOptimizations(); +} + inline bool optimizeForX86() { return isX86() && Options::useArchitectureSpecificOptimizations(); diff --git a/Source/JavaScriptCore/assembler/MIPSAssembler.h b/Source/JavaScriptCore/assembler/MIPSAssembler.h index dc518433e..9fc679086 100644 --- a/Source/JavaScriptCore/assembler/MIPSAssembler.h +++ b/Source/JavaScriptCore/assembler/MIPSAssembler.h @@ -733,35 +733,6 @@ public: // writable region of memory; to modify the code in an execute-only execuable // pool the 'repatch' and 'relink' methods should be used. - static size_t linkDirectJump(void* code, void* to) - { - MIPSWord* insn = reinterpret_cast(reinterpret_cast(code)); - size_t ops = 0; - int32_t slotAddr = reinterpret_cast(insn) + 4; - int32_t toAddr = reinterpret_cast(to); - - if ((slotAddr & 0xf0000000) != (toAddr & 0xf0000000)) { - // lui - *insn = 0x3c000000 | (MIPSRegisters::t9 << OP_SH_RT) | ((toAddr >> 16) & 0xffff); - ++insn; - // ori - *insn = 0x34000000 | (MIPSRegisters::t9 << OP_SH_RT) | (MIPSRegisters::t9 << OP_SH_RS) | (toAddr & 0xffff); - ++insn; - // jr - *insn = 0x00000008 | (MIPSRegisters::t9 << OP_SH_RS); - ++insn; - ops = 4 * sizeof(MIPSWord); - } else { - // j - *insn = 0x08000000 | ((toAddr & 0x0fffffff) >> 2); - ++insn; - ops = 2 * sizeof(MIPSWord); - } - // nop - *insn = 0x00000000; - return ops; - } - void linkJump(AssemblerLabel from, AssemblerLabel to) { ASSERT(to.isSet()); @@ -881,34 +852,42 @@ public: static ptrdiff_t maxJumpReplacementSize() { - return sizeof(MIPSWord) * 4; + return sizeof(MIPSWord) * 2; } static void revertJumpToMove(void* instructionStart, RegisterID rt, int imm) { MIPSWord* insn = static_cast(instructionStart); - size_t codeSize = 2 * sizeof(MIPSWord); // lui *insn = 0x3c000000 | (rt << OP_SH_RT) | ((imm >> 16) & 0xffff); ++insn; // ori *insn = 0x34000000 | (rt << OP_SH_RS) | (rt << OP_SH_RT) | (imm & 0xffff); - ++insn; - // if jr $t9 - if (*insn == 0x03200008) { - *insn = 0x00000000; - codeSize += sizeof(MIPSWord); - } - cacheFlush(insn, codeSize); + cacheFlush(insn, 2 * sizeof(MIPSWord)); + } + + static bool canJumpWithJ(void* instructionStart, void* to) + { + intptr_t slotAddr = reinterpret_cast(instructionStart) + 4; + intptr_t toAddr = reinterpret_cast(to); + return (slotAddr & 0xf0000000) == (toAddr & 0xf0000000); } static void replaceWithJump(void* instructionStart, void* to) { ASSERT(!(bitwise_cast(instructionStart) & 3)); ASSERT(!(bitwise_cast(to) & 3)); - size_t ops = linkDirectJump(instructionStart, to); - cacheFlush(instructionStart, ops); + ASSERT(canJumpWithJ(instructionStart, to)); + MIPSWord* insn = reinterpret_cast(instructionStart); + int32_t toAddr = reinterpret_cast(to); + + // j + *insn = 0x08000000 | ((toAddr & 0x0fffffff) >> 2); + ++insn; + // nop + *insn = 0x00000000; + cacheFlush(instructionStart, 2 * sizeof(MIPSWord)); } static void replaceWithLoad(void* instructionStart) diff --git a/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h b/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h index a1e67e262..d43ffd22a 100644 --- a/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h +++ b/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h @@ -816,7 +816,53 @@ public: void load16Unaligned(BaseIndex address, RegisterID dest) { - load16(address, dest); + if (address.offset >= -32768 && address.offset <= 32767 && !m_fixedWidth) { + /* + sll addrtemp, address.index, address.scale + addu addrtemp, addrtemp, address.base + lbu immTemp, address.offset+x(addrtemp) (x=0 for LE, x=1 for BE) + lbu dest, address.offset+x(addrtemp) (x=1 for LE, x=0 for BE) + sll dest, dest, 8 + or dest, dest, immTemp + */ + m_assembler.sll(addrTempRegister, address.index, address.scale); + m_assembler.addu(addrTempRegister, addrTempRegister, address.base); +#if CPU(BIG_ENDIAN) + m_assembler.lbu(immTempRegister, addrTempRegister, address.offset + 1); + m_assembler.lbu(dest, addrTempRegister, address.offset); +#else + m_assembler.lbu(immTempRegister, addrTempRegister, address.offset); + m_assembler.lbu(dest, addrTempRegister, address.offset + 1); +#endif + m_assembler.sll(dest, dest, 8); + m_assembler.orInsn(dest, dest, immTempRegister); + } else { + /* + sll addrTemp, address.index, address.scale + addu addrTemp, addrTemp, address.base + lui immTemp, address.offset >> 16 + ori immTemp, immTemp, address.offset & 0xffff + addu addrTemp, addrTemp, immTemp + lbu immTemp, x(addrtemp) (x=0 for LE, x=1 for BE) + lbu dest, x(addrtemp) (x=1 for LE, x=0 for BE) + sll dest, dest, 8 + or dest, dest, immTemp + */ + m_assembler.sll(addrTempRegister, address.index, address.scale); + m_assembler.addu(addrTempRegister, addrTempRegister, address.base); + m_assembler.lui(immTempRegister, address.offset >> 16); + m_assembler.ori(immTempRegister, immTempRegister, address.offset); + m_assembler.addu(addrTempRegister, addrTempRegister, immTempRegister); +#if CPU(BIG_ENDIAN) + m_assembler.lbu(immTempRegister, addrTempRegister, 1); + m_assembler.lbu(dest, addrTempRegister, 0); +#else + m_assembler.lbu(immTempRegister, addrTempRegister, 0); + m_assembler.lbu(dest, addrTempRegister, 1); +#endif + m_assembler.sll(dest, dest, 8); + m_assembler.orInsn(dest, dest, immTempRegister); + } } void load32WithUnalignedHalfWords(BaseIndex address, RegisterID dest) @@ -2645,8 +2691,6 @@ public: Jump branchEqual(RegisterID rs, RegisterID rt) { - m_assembler.nop(); - m_assembler.nop(); m_assembler.appendJump(); m_assembler.beq(rs, rt, 0); m_assembler.nop(); @@ -2656,8 +2700,6 @@ public: Jump branchNotEqual(RegisterID rs, RegisterID rt) { - m_assembler.nop(); - m_assembler.nop(); m_assembler.appendJump(); m_assembler.bne(rs, rt, 0); m_assembler.nop(); diff --git a/Source/JavaScriptCore/dfg/DFGFixupPhase.cpp b/Source/JavaScriptCore/dfg/DFGFixupPhase.cpp index c8dd0cb3f..ee294246e 100644 --- a/Source/JavaScriptCore/dfg/DFGFixupPhase.cpp +++ b/Source/JavaScriptCore/dfg/DFGFixupPhase.cpp @@ -282,7 +282,7 @@ private: break; } if (m_graph.binaryArithShouldSpeculateInt32(node, FixupPass)) { - if (optimizeForX86() || optimizeForARM64() || optimizeForARMv7IDIVSupported()) { + if (optimizeForX86() || optimizeForARM64() || optimizeForARMv7IDIVSupported() || optimizeForMIPS()) { fixIntOrBooleanEdge(leftChild); fixIntOrBooleanEdge(rightChild); if (bytecodeCanTruncateInteger(node->arithNodeFlags())) diff --git a/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp b/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp index de2025ada..8c3c40d1e 100644 --- a/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp +++ b/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp @@ -4014,6 +4014,46 @@ void SpeculativeJIT::compileArithDiv(Node* node) } int32Result(quotient.gpr(), node); +#elif CPU(MIPS) + SpeculateInt32Operand op1(this, node->child1()); + SpeculateInt32Operand op2(this, node->child2()); + GPRTemporary quotient(this); + GPRReg op1GPR = op1.gpr(); + GPRReg op2GPR = op2.gpr(); + GPRReg quotientGPR = quotient.gpr(); + JITCompiler::Jump done; + + // If the user cares about negative zero, then speculate that we're not about + // to produce negative zero. + if (!bytecodeCanIgnoreNegativeZero(node->arithNodeFlags())) { + MacroAssembler::Jump numeratorNonZero = m_jit.branchTest32(MacroAssembler::NonZero, op1GPR); + speculationCheck(NegativeZero, JSValueRegs(), 0, m_jit.branch32(MacroAssembler::LessThan, op2GPR, TrustedImm32(0))); + numeratorNonZero.link(&m_jit); + } + + if (bytecodeUsesAsNumber(node->arithNodeFlags())) { + speculationCheck(Overflow, JSValueRegs(), 0, m_jit.branchTest32(JITCompiler::Zero, op2GPR)); + speculationCheck(Overflow, JSValueRegs(), 0, m_jit.branch32(JITCompiler::Equal, op1GPR, TrustedImm32(-2147483647-1))); + } else { + JITCompiler::Jump notZero = m_jit.branchTest32(JITCompiler::NonZero, op2GPR); + m_jit.move(TrustedImm32(0), quotientGPR); + done = m_jit.jump(); + notZero.link(&m_jit); + } + + m_jit.assembler().div(op1GPR, op2GPR); + m_jit.assembler().mflo(quotientGPR); + + // Check that there was no remainder. If there had been, then we'd be obligated to + // produce a double result instead. + if (bytecodeUsesAsNumber(node->arithNodeFlags())) { + GPRTemporary remainder(this); + m_jit.assembler().mfhi(remainder.gpr()); + speculationCheck(Overflow, JSValueRegs(), 0, m_jit.branchTest32(MacroAssembler::NonZero, remainder.gpr())); + } else + done.link(&m_jit); + + int32Result(quotientGPR, node); #else RELEASE_ASSERT_NOT_REACHED(); #endif @@ -4394,6 +4434,24 @@ void SpeculativeJIT::compileArithMod(Node* node) done.link(&m_jit); int32Result(quotientThenRemainderGPR, node); +#elif CPU(MIPS) + GPRTemporary remainder(this); + GPRReg dividendGPR = op1.gpr(); + GPRReg divisorGPR = op2.gpr(); + GPRReg remainderGPR = remainder.gpr(); + + speculationCheck(Overflow, JSValueRegs(), 0, m_jit.branch32(JITCompiler::Equal, dividendGPR, TrustedImm32(-2147483647-1))); + m_jit.assembler().div(dividendGPR, divisorGPR); + m_jit.assembler().mfhi(remainderGPR); + + if (!bytecodeCanIgnoreNegativeZero(node->arithNodeFlags())) { + // Check that we're not about to create negative zero. + JITCompiler::Jump numeratorPositive = m_jit.branch32(JITCompiler::GreaterThanOrEqual, dividendGPR, TrustedImm32(0)); + speculationCheck(NegativeZero, JSValueRegs(), 0, m_jit.branchTest32(JITCompiler::Zero, remainderGPR)); + numeratorPositive.link(&m_jit); + } + + int32Result(remainderGPR, node); #else // not architecture that can do integer division RELEASE_ASSERT_NOT_REACHED(); #endif diff --git a/Source/JavaScriptCore/disassembler/udis86/differences.txt b/Source/JavaScriptCore/disassembler/udis86/differences.txt index dc225b6ff..c3dabf6f0 100644 --- a/Source/JavaScriptCore/disassembler/udis86/differences.txt +++ b/Source/JavaScriptCore/disassembler/udis86/differences.txt @@ -5,20 +5,5 @@ here: - assert() has been changed to ASSERT() -- Mass rename of udis86_input.h inp_ prefixed functions and macros to ud_inp_ to - avoid namespace pollution. - -- Removal of KERNEL checks. - -- Added #include of udis86_extern.h in udis86_decode.c. - -- Removed s_ie__pause and s_ie__nop from udis86_decode.c, since they weren't used. - -- Made udis86_syn.h use WTF_ATTRIBUTE_PRINTF. This required making a bunch of little - fixes to make the compiler's format string warnings go away. - -- Made the code in udis86_syn.h use vsnprintf() instead of vsprintf(). - - Fixed udis86_syn-att.c's jump destination printing to work correctly in 64-bit mode. -- Add --outputDir option to itab.py. diff --git a/Source/JavaScriptCore/disassembler/udis86/itab.py b/Source/JavaScriptCore/disassembler/udis86/itab.py deleted file mode 100644 index 3d50ad061..000000000 --- a/Source/JavaScriptCore/disassembler/udis86/itab.py +++ /dev/null @@ -1,360 +0,0 @@ -# udis86 - scripts/itab.py -# -# Copyright (c) 2009 Vivek Thampi -# All rights reserved. -# -# Redistribution and use in source and binary forms, with or without modification, -# are permitted provided that the following conditions are met: -# -# * Redistributions of source code must retain the above copyright notice, -# this list of conditions and the following disclaimer. -# * Redistributions in binary form must reproduce the above copyright notice, -# this list of conditions and the following disclaimer in the documentation -# and/or other materials provided with the distribution. -# -# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED -# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE -# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR -# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES -# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; -# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON -# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -from optparse import OptionParser -import os -import sys - -sys.path.append( '../scripts' ); - -import ud_optable -import ud_opcode - -class UdItabGenerator( ud_opcode.UdOpcodeTables ): - - OperandDict = { - "Ap" : [ "OP_A" , "SZ_P" ], - "E" : [ "OP_E" , "SZ_NA" ], - "Eb" : [ "OP_E" , "SZ_B" ], - "Ew" : [ "OP_E" , "SZ_W" ], - "Ev" : [ "OP_E" , "SZ_V" ], - "Ed" : [ "OP_E" , "SZ_D" ], - "Eq" : [ "OP_E" , "SZ_Q" ], - "Ez" : [ "OP_E" , "SZ_Z" ], - "Ex" : [ "OP_E" , "SZ_MDQ" ], - "Ep" : [ "OP_E" , "SZ_P" ], - "G" : [ "OP_G" , "SZ_NA" ], - "Gb" : [ "OP_G" , "SZ_B" ], - "Gw" : [ "OP_G" , "SZ_W" ], - "Gv" : [ "OP_G" , "SZ_V" ], - "Gy" : [ "OP_G" , "SZ_MDQ" ], - "Gy" : [ "OP_G" , "SZ_MDQ" ], - "Gd" : [ "OP_G" , "SZ_D" ], - "Gq" : [ "OP_G" , "SZ_Q" ], - "Gx" : [ "OP_G" , "SZ_MDQ" ], - "Gz" : [ "OP_G" , "SZ_Z" ], - "M" : [ "OP_M" , "SZ_NA" ], - "Mb" : [ "OP_M" , "SZ_B" ], - "Mw" : [ "OP_M" , "SZ_W" ], - "Ms" : [ "OP_M" , "SZ_W" ], - "Md" : [ "OP_M" , "SZ_D" ], - "Mq" : [ "OP_M" , "SZ_Q" ], - "Mt" : [ "OP_M" , "SZ_T" ], - "Mo" : [ "OP_M" , "SZ_O" ], - "MwRv" : [ "OP_MR" , "SZ_WV" ], - "MdRy" : [ "OP_MR" , "SZ_DY" ], - "MbRv" : [ "OP_MR" , "SZ_BV" ], - "I1" : [ "OP_I1" , "SZ_NA" ], - "I3" : [ "OP_I3" , "SZ_NA" ], - "Ib" : [ "OP_I" , "SZ_B" ], - "Isb" : [ "OP_I" , "SZ_SB" ], - "Iw" : [ "OP_I" , "SZ_W" ], - "Iv" : [ "OP_I" , "SZ_V" ], - "Iz" : [ "OP_I" , "SZ_Z" ], - "Jv" : [ "OP_J" , "SZ_V" ], - "Jz" : [ "OP_J" , "SZ_Z" ], - "Jb" : [ "OP_J" , "SZ_B" ], - "R" : [ "OP_R" , "SZ_RDQ" ], - "C" : [ "OP_C" , "SZ_NA" ], - "D" : [ "OP_D" , "SZ_NA" ], - "S" : [ "OP_S" , "SZ_NA" ], - "Ob" : [ "OP_O" , "SZ_B" ], - "Ow" : [ "OP_O" , "SZ_W" ], - "Ov" : [ "OP_O" , "SZ_V" ], - "V" : [ "OP_V" , "SZ_O" ], - "W" : [ "OP_W" , "SZ_O" ], - "Wsd" : [ "OP_W" , "SZ_O" ], - "Wss" : [ "OP_W" , "SZ_O" ], - "P" : [ "OP_P" , "SZ_Q" ], - "Q" : [ "OP_Q" , "SZ_Q" ], - "VR" : [ "OP_VR" , "SZ_O" ], - "PR" : [ "OP_PR" , "SZ_Q" ], - "AL" : [ "OP_AL" , "SZ_NA" ], - "CL" : [ "OP_CL" , "SZ_NA" ], - "DL" : [ "OP_DL" , "SZ_NA" ], - "BL" : [ "OP_BL" , "SZ_NA" ], - "AH" : [ "OP_AH" , "SZ_NA" ], - "CH" : [ "OP_CH" , "SZ_NA" ], - "DH" : [ "OP_DH" , "SZ_NA" ], - "BH" : [ "OP_BH" , "SZ_NA" ], - "AX" : [ "OP_AX" , "SZ_NA" ], - "CX" : [ "OP_CX" , "SZ_NA" ], - "DX" : [ "OP_DX" , "SZ_NA" ], - "BX" : [ "OP_BX" , "SZ_NA" ], - "SI" : [ "OP_SI" , "SZ_NA" ], - "DI" : [ "OP_DI" , "SZ_NA" ], - "SP" : [ "OP_SP" , "SZ_NA" ], - "BP" : [ "OP_BP" , "SZ_NA" ], - "eAX" : [ "OP_eAX" , "SZ_NA" ], - "eCX" : [ "OP_eCX" , "SZ_NA" ], - "eDX" : [ "OP_eDX" , "SZ_NA" ], - "eBX" : [ "OP_eBX" , "SZ_NA" ], - "eSI" : [ "OP_eSI" , "SZ_NA" ], - "eDI" : [ "OP_eDI" , "SZ_NA" ], - "eSP" : [ "OP_eSP" , "SZ_NA" ], - "eBP" : [ "OP_eBP" , "SZ_NA" ], - "rAX" : [ "OP_rAX" , "SZ_NA" ], - "rCX" : [ "OP_rCX" , "SZ_NA" ], - "rBX" : [ "OP_rBX" , "SZ_NA" ], - "rDX" : [ "OP_rDX" , "SZ_NA" ], - "rSI" : [ "OP_rSI" , "SZ_NA" ], - "rDI" : [ "OP_rDI" , "SZ_NA" ], - "rSP" : [ "OP_rSP" , "SZ_NA" ], - "rBP" : [ "OP_rBP" , "SZ_NA" ], - "ES" : [ "OP_ES" , "SZ_NA" ], - "CS" : [ "OP_CS" , "SZ_NA" ], - "DS" : [ "OP_DS" , "SZ_NA" ], - "SS" : [ "OP_SS" , "SZ_NA" ], - "GS" : [ "OP_GS" , "SZ_NA" ], - "FS" : [ "OP_FS" , "SZ_NA" ], - "ST0" : [ "OP_ST0" , "SZ_NA" ], - "ST1" : [ "OP_ST1" , "SZ_NA" ], - "ST2" : [ "OP_ST2" , "SZ_NA" ], - "ST3" : [ "OP_ST3" , "SZ_NA" ], - "ST4" : [ "OP_ST4" , "SZ_NA" ], - "ST5" : [ "OP_ST5" , "SZ_NA" ], - "ST6" : [ "OP_ST6" , "SZ_NA" ], - "ST7" : [ "OP_ST7" , "SZ_NA" ], - "NONE" : [ "OP_NONE" , "SZ_NA" ], - "ALr8b" : [ "OP_ALr8b" , "SZ_NA" ], - "CLr9b" : [ "OP_CLr9b" , "SZ_NA" ], - "DLr10b" : [ "OP_DLr10b" , "SZ_NA" ], - "BLr11b" : [ "OP_BLr11b" , "SZ_NA" ], - "AHr12b" : [ "OP_AHr12b" , "SZ_NA" ], - "CHr13b" : [ "OP_CHr13b" , "SZ_NA" ], - "DHr14b" : [ "OP_DHr14b" , "SZ_NA" ], - "BHr15b" : [ "OP_BHr15b" , "SZ_NA" ], - "rAXr8" : [ "OP_rAXr8" , "SZ_NA" ], - "rCXr9" : [ "OP_rCXr9" , "SZ_NA" ], - "rDXr10" : [ "OP_rDXr10" , "SZ_NA" ], - "rBXr11" : [ "OP_rBXr11" , "SZ_NA" ], - "rSPr12" : [ "OP_rSPr12" , "SZ_NA" ], - "rBPr13" : [ "OP_rBPr13" , "SZ_NA" ], - "rSIr14" : [ "OP_rSIr14" , "SZ_NA" ], - "rDIr15" : [ "OP_rDIr15" , "SZ_NA" ], - "jWP" : [ "OP_J" , "SZ_WP" ], - "jDP" : [ "OP_J" , "SZ_DP" ], - - } - - # - # opcode prefix dictionary - # - PrefixDict = { - "aso" : "P_aso", - "oso" : "P_oso", - "rexw" : "P_rexw", - "rexb" : "P_rexb", - "rexx" : "P_rexx", - "rexr" : "P_rexr", - "seg" : "P_seg", - "inv64" : "P_inv64", - "def64" : "P_def64", - "depM" : "P_depM", - "cast1" : "P_c1", - "cast2" : "P_c2", - "cast3" : "P_c3", - "cast" : "P_cast", - "sext" : "P_sext" - } - - InvalidEntryIdx = 0 - InvalidEntry = { 'type' : 'invalid', - 'mnemonic' : 'invalid', - 'operands' : '', - 'prefixes' : '', - 'meta' : '' } - - Itab = [] # instruction table - ItabIdx = 1 # instruction table index - GtabIdx = 0 # group table index - GtabMeta = [] - - ItabLookup = {} - - MnemonicAliases = ( "invalid", "3dnow", "none", "db", "pause" ) - - def __init__( self, outputDir ): - # first itab entry (0) is Invalid - self.Itab.append( self.InvalidEntry ) - self.MnemonicsTable.extend( self.MnemonicAliases ) - self.outputDir = outputDir - - def toGroupId( self, id ): - return 0x8000 | id - - def genLookupTable( self, table, scope = '' ): - idxArray = [ ] - ( tabIdx, self.GtabIdx ) = ( self.GtabIdx, self.GtabIdx + 1 ) - self.GtabMeta.append( { 'type' : table[ 'type' ], 'meta' : table[ 'meta' ] } ) - - for _idx in range( self.sizeOfTable( table[ 'type' ] ) ): - idx = "%02x" % _idx - - e = self.InvalidEntry - i = self.InvalidEntryIdx - - if idx in table[ 'entries' ].keys(): - e = table[ 'entries' ][ idx ] - - # leaf node (insn) - if e[ 'type' ] == 'insn': - ( i, self.ItabIdx ) = ( self.ItabIdx, self.ItabIdx + 1 ) - self.Itab.append( e ) - elif e[ 'type' ] != 'invalid': - i = self.genLookupTable( e, 'static' ) - - idxArray.append( i ) - - name = "ud_itab__%s" % tabIdx - self.ItabLookup[ tabIdx ] = name - - self.ItabC.write( "\n" ); - if len( scope ): - self.ItabC.write( scope + ' ' ) - self.ItabC.write( "const uint16_t %s[] = {\n" % name ) - for i in range( len( idxArray ) ): - if i > 0 and i % 4 == 0: - self.ItabC.write( "\n" ) - if ( i%4 == 0 ): - self.ItabC.write( " /* %2x */" % i) - if idxArray[ i ] >= 0x8000: - self.ItabC.write( "%12s," % ("GROUP(%d)" % ( ~0x8000 & idxArray[ i ] ))) - else: - self.ItabC.write( "%12d," % ( idxArray[ i ] )) - self.ItabC.write( "\n" ) - self.ItabC.write( "};\n" ) - - return self.toGroupId( tabIdx ) - - def genLookupTableList( self ): - self.ItabC.write( "\n\n" ); - self.ItabC.write( "struct ud_lookup_table_list_entry ud_lookup_table_list[] = {\n" ) - for i in range( len( self.GtabMeta ) ): - f0 = self.ItabLookup[ i ] + "," - f1 = ( self.nameOfTable( self.GtabMeta[ i ][ 'type' ] ) ) + "," - f2 = "\"%s\"" % self.GtabMeta[ i ][ 'meta' ] - self.ItabC.write( " /* %03d */ { %s %s %s },\n" % ( i, f0, f1, f2 ) ) - self.ItabC.write( "};" ) - - def genInsnTable( self ): - self.ItabC.write( "struct ud_itab_entry ud_itab[] = {\n" ); - idx = 0 - for e in self.Itab: - opr_c = [ "O_NONE", "O_NONE", "O_NONE" ] - pfx_c = [] - opr = e[ 'operands' ] - for i in range(len(opr)): - if not (opr[i] in self.OperandDict.keys()): - print("error: invalid operand declaration: %s\n" % opr[i]) - opr_c[i] = "O_" + opr[i] - opr = "%s %s %s" % (opr_c[0] + ",", opr_c[1] + ",", opr_c[2]) - - for p in e['prefixes']: - if not ( p in self.PrefixDict.keys() ): - print("error: invalid prefix specification: %s \n" % pfx) - pfx_c.append( self.PrefixDict[p] ) - if len(e['prefixes']) == 0: - pfx_c.append( "P_none" ) - pfx = "|".join( pfx_c ) - - self.ItabC.write( " /* %04d */ { UD_I%s %s, %s },\n" \ - % ( idx, e[ 'mnemonic' ] + ',', opr, pfx ) ) - idx += 1 - self.ItabC.write( "};\n" ) - - self.ItabC.write( "\n\n" ); - self.ItabC.write( "const char * ud_mnemonics_str[] = {\n" ) - self.ItabC.write( ",\n ".join( [ "\"%s\"" % m for m in self.MnemonicsTable ] ) ) - self.ItabC.write( "\n};\n" ) - - - def genItabH( self ): - self.ItabH = open( os.path.join(self.outputDir, "udis86_itab.h"), "w" ) - - # Generate Table Type Enumeration - self.ItabH.write( "#ifndef UD_ITAB_H\n" ) - self.ItabH.write( "#define UD_ITAB_H\n\n" ) - - # table type enumeration - self.ItabH.write( "/* ud_table_type -- lookup table types (see lookup.c) */\n" ) - self.ItabH.write( "enum ud_table_type {\n " ) - enum = [ self.TableInfo[ k ][ 'name' ] for k in self.TableInfo.keys() ] - self.ItabH.write( ",\n ".join( enum ) ) - self.ItabH.write( "\n};\n\n" ); - - # mnemonic enumeration - self.ItabH.write( "/* ud_mnemonic -- mnemonic constants */\n" ) - enum = "enum ud_mnemonic_code {\n " - enum += ",\n ".join( [ "UD_I%s" % m for m in self.MnemonicsTable ] ) - enum += "\n} UD_ATTR_PACKED;\n" - self.ItabH.write( enum ) - self.ItabH.write( "\n" ) - - self.ItabH.write("\n/* itab entry operand definitions */\n"); - operands = self.OperandDict.keys() - operands.sort() - for o in operands: - self.ItabH.write("#define O_%-7s { %-12s %-8s }\n" % - (o, self.OperandDict[o][0] + ",", self.OperandDict[o][1])); - self.ItabH.write("\n\n"); - - self.ItabH.write( "extern const char * ud_mnemonics_str[];\n" ) - - self.ItabH.write( "#define GROUP(n) (0x8000 | (n))" ) - - self.ItabH.write( "\n#endif /* UD_ITAB_H */\n" ) - - self.ItabH.close() - - - def genItabC( self ): - self.ItabC = open( os.path.join(self.outputDir, "udis86_itab.c"), "w" ) - self.ItabC.write( "/* itab.c -- generated by itab.py, do no edit" ) - self.ItabC.write( " */\n" ); - self.ItabC.write( "#include \"udis86_decode.h\"\n\n" ); - - self.genLookupTable( self.OpcodeTable0 ) - self.genLookupTableList() - self.genInsnTable() - - self.ItabC.close() - - def genItab( self ): - self.genItabC() - self.genItabH() - -def main(): - parser = OptionParser() - parser.add_option("--outputDir", dest="outputDir", default="") - options, args = parser.parse_args() - generator = UdItabGenerator(os.path.normpath(options.outputDir)) - optableXmlParser = ud_optable.UdOptableXmlParser() - optableXmlParser.parse( args[ 0 ], generator.addInsnDef ) - - generator.genItab() - -if __name__ == '__main__': - main() diff --git a/Source/JavaScriptCore/disassembler/udis86/optable.xml b/Source/JavaScriptCore/disassembler/udis86/optable.xml index 14b4ac593..3bda8587e 100644 --- a/Source/JavaScriptCore/disassembler/udis86/optable.xml +++ b/Source/JavaScriptCore/disassembler/udis86/optable.xml @@ -2,37 +2,132 @@ + + aaa - 37 - inv64 + 37 /m=!64 aad - d5 + d5 /m=!64 Ib - inv64 aam - d4 + d4 /m=!64 Ib - inv64 aas - 3f - inv64 + 3f /m=!64 @@ -65,8 +160,7 @@ oso rexw 15 - rAX Iz - sext + rAX sIz aso rexr rexx rexb @@ -75,21 +169,19 @@ aso rexr rexx rexb - 82 /reg=2 + 82 /reg=2 /m=!64 Eb Ib inv64 aso oso rexw rexr rexx rexb 81 /reg=2 - Ev Iz - sext + Ev sIz aso oso rexw rexr rexx rexb 83 /reg=2 - Ev Ib - sext + Ev sIb @@ -122,8 +214,7 @@ oso rexw 05 - rAX Iz - sext + rAX sIz aso rexr rexx rexb @@ -132,43 +223,39 @@ aso rexr rexx rexb - 82 /reg=0 + 82 /reg=0 /m=!64 Eb Ib inv64 aso oso rexw rexr rexx rexb 81 /reg=0 - Ev Iz - sext + Ev sIz aso oso rexw rexr rexx rexb 83 /reg=0 - Ev Ib - sext + Ev sIb - - addpd - aso rexr rexx rexb - sse66 0f 58 - V W + aso rexr rexx rexb vexl + /sse=66 0f 58 + V H W + sse2 avx addps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 58 - V W + V H W + sse avx @@ -176,8 +263,9 @@ addsd aso rexr rexx rexb - ssef2 0f 58 - V W + /sse=f2 0f 58 + V H W + sse2 avx @@ -185,12 +273,94 @@ addss aso rexr rexx rexb - ssef3 0f 58 + /sse=f3 0f 58 + V H W + sse avx + + + + + addsubpd + + aso rexr rexx rexb + /sse=66 0f d0 + V H W + sse3 avx + + + + + addsubps + + aso rexr rexx rexb + /sse=f2 0f d0 + V H W + sse3 avx + + + + + aesdec + + aso rexr rexx rexb + /sse=66 0f 38 de + V H W + aesni avx + + + + + aesdeclast + + aso rexr rexx rexb + /sse=66 0f 38 df V W + aesni avx - + + aesenc + aesni + + aso rexr rexx rexb + /sse=66 0f 38 dc + V W + aesni avx + + + + + aesenclast + aesni avx + + aso rexr rexx rexb + /sse=66 0f 38 dd + V H W + + + + + aesimc + + aso rexr rexx rexb + /sse=66 0f 38 db + V W + aesni avx + + + + + aeskeygenassist + + aso rexr rexx rexb + /sse=66 0f 3a df + V W Ib + aesni avx + + + + and aso rexr rexx rexb @@ -219,8 +389,7 @@ oso rexw 25 - rAX Iz - sext + rAX sIz aso rexw rexr rexx rexb @@ -229,30 +398,29 @@ aso rexr rexx rexb - 82 /reg=4 + 82 /reg=4 /m=!64 Eb Ib inv64 aso oso rexw rexr rexx rexb 81 /reg=4 - Ev Iz - sext + Ev sIz aso oso rexw rexr rexx rexb 83 /reg=4 - Ev Ib - sext + Ev sIb andpd - aso rexr rexx rexb - sse66 0f 54 - V W + aso rexr rexx rexb vexl + /sse=66 0f 54 + V H W + sse2 avx @@ -261,7 +429,8 @@ aso rexr rexx rexb 0f 54 - V W + V H W + sse avx @@ -269,8 +438,9 @@ andnpd aso rexr rexx rexb - sse66 0f 55 - V W + /sse=66 0f 55 + V H W + sse2 avx @@ -279,7 +449,8 @@ aso rexr rexx rexb 0f 55 - V W + V H W + sse2 avx @@ -287,15 +458,8 @@ arpl aso - 63 /m=16 - Ew Gw - inv64 - - - aso - 63 /m=32 + 63 /m=!64 Ew Gw - inv64 @@ -304,150 +468,27 @@ aso oso rexw rexx rexr rexb 63 /m=64 - Gv Ed - - - - - bound - - aso oso - 62 - Gv M - inv64 - - - - - bsf - - aso oso rexw rexr rexx rexb - 0f bc - Gv Ev - - - - - bsr - - aso oso rexw rexr rexx rexb - 0f bd - Gv Ev - - - - - bswap - - oso rexw rexb - 0f c8 - rAXr8 - - - oso rexw rexb - 0f c9 - rCXr9 - - - oso rexw rexb - 0f ca - rDXr10 - - - oso rexw rexb - 0f cb - rBXr11 - - - oso rexw rexb - 0f cc - rSPr12 - - - oso rexw rexb - 0f cd - rBPr13 - - - oso rexw rexb - 0f ce - rSIr14 - - - oso rexw rexb - 0f cf - rDIr15 - - - - - bt - - aso oso rexw rexr rexx rexb - 0f ba /reg=4 - Ev Ib - - - aso oso rexw rexr rexx rexb - 0f a3 - Ev Gv - - - - - btc - - aso oso rexw rexr rexx rexb - 0f bb - Ev Gv - - - aso oso rexw rexr rexx rexb - 0f ba /reg=7 - Ev Ib + Gq Ed - btr - - aso oso rexw rexr rexx rexb - 0f b3 - Ev Gv - - - aso oso rexw rexr rexx rexb - 0f ba /reg=6 - Ev Ib - - - - - bts - - aso oso rexw rexr rexx rexb - 0f ab - Ev Gv - + call aso oso rexw rexr rexx rexb - 0f ba /reg=5 - Ev Ib + ff /reg=2 /m=!64 + Ev - - - - call aso oso rexw rexr rexx rexb - ff /reg=2 - Ev + ff /reg=2 /m=64 + Eq def64 aso oso rexw rexr rexx rexb ff /reg=3 - Ep + Fv oso @@ -457,9 +498,8 @@ oso - 9a - Ap - inv64 + 9a /m=!64 + Av @@ -712,7 +752,7 @@ oso rexw 3d - rAX Iz + rAX sIz aso rexr rexx rexb @@ -721,43 +761,46 @@ aso rexr rexx rexb - 82 /reg=7 + 82 /reg=7 /m=!64 Eb Ib inv64 aso oso rexw rexr rexx rexb 81 /reg=7 - Ev Iz + Ev sIz aso oso rexw rexr rexx rexb 83 /reg=7 - Ev Ib + Ev sIb cmppd - aso rexr rexx rexb - sse66 0f c2 - V W Ib + aso rexr rexx rexb vexl + /sse=66 0f c2 + V H W Ib + sse2 avx cmpps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f c2 - V W Ib + V H W Ib + sse2 avx cmpsb + repz seg a6 @@ -765,7 +808,7 @@ cmpsw - oso rexw + repz oso rexw seg a7 /o=16 @@ -773,20 +816,21 @@ cmpsd - oso rexw + repz oso rexw seg a7 /o=32 aso rexr rexx rexb - ssef2 0f c2 - V W Ib + /sse=f2 0f c2 + V H W Ib + sse2 avx cmpsq - oso rexw + repz oso rexw seg a7 /o=64 @@ -795,8 +839,9 @@ cmpss aso rexr rexx rexb - ssef3 0f c2 - V W Ib + /sse=f3 0f c2 + V H W Ib + sse2 avx @@ -818,7 +863,21 @@ cmpxchg8b aso rexr rexx rexb - 0f c7 /reg=1 + 0f c7 /mod=!11 /reg=1 /o=16 + M + + + aso rexr rexx rexb + 0f c7 /mod=!11 /reg=1 /o=32 + M + + + + + cmpxchg16b + + aso rexr rexx rexb + 0f c7 /mod=!11 /reg=1 /o=64 M @@ -827,8 +886,9 @@ comisd aso rexr rexx rexb - sse66 0f 2f - V W + /sse=66 0f 2f + Vsd Wsd + sse2 avx @@ -838,6 +898,7 @@ aso rexr rexx rexb 0f 2f V W + sse2 avx @@ -851,9 +912,10 @@ cvtdq2pd - aso rexr rexx rexb - ssef3 0f e6 - V W + aso rexr rexx rexb vexl + /sse=f3 0f e6 + V Wdq + sse2 avx @@ -863,15 +925,17 @@ aso rexr rexx rexb 0f 5b V W + sse2 avx cvtpd2dq - aso rexr rexx rexb - ssef2 0f e6 - V W + aso rexr rexx rexb vexl + /sse=f2 0f e6 + Vdq W + sse2 avx @@ -879,7 +943,7 @@ cvtpd2pi aso rexr rexx rexb - sse66 0f 2d + /sse=66 0f 2d P W @@ -887,9 +951,10 @@ cvtpd2ps - aso rexr rexx rexb - sse66 0f 5a - V W + aso rexr rexx rexb vexl + /sse=66 0f 5a + Vdq W + sse2 avx @@ -906,7 +971,7 @@ cvtpi2pd aso rexr rexx rexb - sse66 0f 2a + /sse=66 0f 2a V Q @@ -914,27 +979,29 @@ cvtps2dq - aso rexr rexx rexb - sse66 0f 5b + aso rexr rexx rexb vexl + /sse=66 0f 5b V W + sse2 avx - cvtps2pi + cvtps2pd - aso rexr rexx rexb - 0f 2d - P W + aso rexr rexx rexb vexl + 0f 5a + V Wdq + sse2 avx - cvtps2pd + cvtps2pi aso rexr rexx rexb - 0f 5a - V W + 0f 2d + P MqU @@ -942,8 +1009,9 @@ cvtsd2si aso rexw rexr rexx rexb - ssef2 0f 2d - Gy W + /sse=f2 0f 2d + Gy MqU + sse2 avx @@ -951,26 +1019,29 @@ cvtsd2ss aso rexr rexx rexb - ssef2 0f 5a - V W + /sse=f2 0f 5a + V H W + sse2 avx - cvtsi2ss + cvtsi2sd aso rexw rexr rexx rexb - ssef3 0f 2a - V Ex + /sse=f2 0f 2a + V H Ey + sse2 avx - cvtss2si + cvtsi2ss aso rexw rexr rexx rexb - ssef3 0f 2d - Gy W + /sse=f3 0f 2a + V H Ey + sse avx @@ -978,35 +1049,48 @@ cvtss2sd aso rexr rexx rexb - ssef3 0f 5a - V W + /sse=f3 0f 5a + V H W + sse2 avx - cvttpd2pi + cvtss2si - aso rexr rexx rexb - sse66 0f 2c - P W + aso rexw rexr rexx rexb + /sse=f3 0f 2d + Gy MdU + sse avx cvttpd2dq + + aso rexr rexx rexb vexl + /sse=66 0f e6 + Vdq W + sse2 avx + + + + + cvttpd2pi aso rexr rexx rexb - sse66 0f e6 - V W + /sse=66 0f 2c + P W cvttps2dq - aso rexr rexx rexb - ssef3 0f 5b + aso rexr rexx rexb vexl + /sse=f3 0f 5b V W + sse2 avx @@ -1023,17 +1107,9 @@ cvttsd2si aso rexw rexr rexx rexb - ssef2 0f 2c - Gy Wsd - - - - - cvtsi2sd - - aso rexw rexr rexx rexb - ssef2 0f 2a - V Ex + /sse=f2 0f 2c + Gy MqU + sse2 avx @@ -1041,8 +1117,9 @@ cvttss2si aso rexw rexr rexx rexb - ssef3 0f 2c - Gy Wsd + /sse=f3 0f 2c + Gy MdU + sse2 avx @@ -1073,7 +1150,7 @@ daa - 27 + 27 /m=!64 inv64 @@ -1081,7 +1158,7 @@ das - 2f + 2f /m=!64 inv64 @@ -1091,42 +1168,42 @@ oso 48 - eAX + R0z oso 49 - eCX + R1z oso 4a - eDX + R2z oso 4b - eBX + R3z oso 4c - eSP + R4z oso 4d - eBP + R5z oso 4e - eSI + R6z oso 4f - eDI + R7z aso rexw rexr rexx rexb @@ -1157,9 +1234,10 @@ divpd - aso rexr rexx rexb - sse66 0f 5e - V W + aso rexr rexx rexb vexl + /sse=66 0f 5e + V H W + sse2 avx @@ -1168,7 +1246,8 @@ aso rexr rexx rexb 0f 5e - V W + V H W + sse avx @@ -1176,8 +1255,9 @@ divsd aso rexr rexx rexb - ssef2 0f 5e - V W + /sse=f2 0f 5e + V H MqU + sse2 avx @@ -1185,8 +1265,29 @@ divss aso rexr rexx rexb - ssef3 0f 5e - V W + /sse=f3 0f 5e + V H MdU + sse avx + + + + + dppd + + aso rexr rexx rexb + /sse=66 0f 3a 41 + V H W Ib + sse4.1 avx + + + + + dpps + + aso rexr rexx rexb vexl + /sse=66 0f 3a 40 + V H W Ib + sse4.1 avx @@ -1202,13 +1303,23 @@ c8 Iw Ib - def64 depM + def64 + + + + + extractps + + aso rexr rexw rexx rexb + /sse=66 0f 3a 17 + MdRy V Ib + sse4.1 avx f2xm1 - X87 + X87 d9 /mod=11 /x87=30 @@ -1216,7 +1327,7 @@ fabs - X87 + X87 d9 /mod=11 /x87=21 @@ -1224,7 +1335,7 @@ fadd - X87 + X87 aso rexr rexx rexb dc /mod=!11 /reg=0 @@ -1303,7 +1414,7 @@ faddp - X87 + X87 de /mod=11 /x87=00 ST0 ST0 @@ -1340,7 +1451,7 @@ fbld - X87 + X87 aso rexr rexx rexb df /mod=!11 /reg=4 @@ -1350,7 +1461,7 @@ fbstp - X87 + X87 aso rexr rexx rexb df /mod=!11 /reg=6 @@ -1360,7 +1471,7 @@ fchs - X87 + X87 d9 /mod=11 /x87=20 @@ -1368,7 +1479,7 @@ fclex - X87 + X87 db /mod=11 /x87=22 @@ -1376,7 +1487,7 @@ fcmovb - X87 + X87 da /mod=11 /x87=00 ST0 ST0 @@ -1413,7 +1524,7 @@ fcmove - X87 + X87 da /mod=11 /x87=08 ST0 ST0 @@ -1450,7 +1561,7 @@ fcmovbe - X87 + X87 da /mod=11 /x87=10 ST0 ST0 @@ -1487,7 +1598,7 @@ fcmovu - X87 + X87 da /mod=11 /x87=18 ST0 ST0 @@ -1524,7 +1635,7 @@ fcmovnb - X87 + X87 db /mod=11 /x87=00 ST0 ST0 @@ -1561,7 +1672,7 @@ fcmovne - X87 + X87 db /mod=11 /x87=08 ST0 ST0 @@ -1598,7 +1709,7 @@ fcmovnbe - X87 + X87 db /mod=11 /x87=10 ST0 ST0 @@ -1635,7 +1746,7 @@ fcmovnu - X87 + X87 db /mod=11 /x87=18 ST0 ST0 @@ -1672,7 +1783,7 @@ fucomi - X87 + X87 db /mod=11 /x87=28 ST0 ST0 @@ -1709,7 +1820,7 @@ fcom - X87 + X87 aso rexr rexx rexb d8 /mod=!11 /reg=2 @@ -1756,7 +1867,7 @@ fcom2 - X87 UNDOC + X87 UNDOC dc /mod=11 /x87=10 ST0 @@ -1793,7 +1904,7 @@ fcomp3 - X87 UNDOC + X87 UNDOC dc /mod=11 /x87=18 ST0 @@ -1830,7 +1941,7 @@ fcomi - X87 + X87 db /mod=11 /x87=30 ST0 ST0 @@ -1867,7 +1978,7 @@ fucomip - X87 + X87 df /mod=11 /x87=28 ST0 ST0 @@ -1904,7 +2015,7 @@ fcomip - X87 + X87 df /mod=11 /x87=30 ST0 ST0 @@ -1941,7 +2052,7 @@ fcomp - X87 + X87 aso rexr rexx rexb d8 /mod=!11 /reg=3 @@ -1988,7 +2099,7 @@ fcomp5 - X87 UNDOC + X87 UNDOC de /mod=11 /x87=10 ST0 @@ -2025,7 +2136,7 @@ fcompp - X87 + X87 de /mod=11 /x87=19 @@ -2033,7 +2144,7 @@ fcos - X87 + X87 d9 /mod=11 /x87=3f @@ -2041,7 +2152,7 @@ fdecstp - X87 + X87 d9 /mod=11 /x87=36 @@ -2049,7 +2160,7 @@ fdiv - X87 + X87 aso rexr rexx rexb dc /mod=!11 /reg=6 @@ -2128,7 +2239,7 @@ fdivp - X87 + X87 de /mod=11 /x87=38 ST0 ST0 @@ -2165,7 +2276,7 @@ fdivr - X87 + X87 aso rexr rexx rexb dc /mod=!11 /reg=7 @@ -2244,7 +2355,7 @@ fdivrp - X87 + X87 de /mod=11 /x87=30 ST0 ST0 @@ -2288,7 +2399,7 @@ ffree - X87 + X87 dd /mod=11 /x87=00 ST0 @@ -2325,7 +2436,7 @@ ffreep - X87 + X87 df /mod=11 /x87=00 ST0 @@ -2362,7 +2473,7 @@ ficom - X87 + X87 aso rexr rexx rexb de /mod=!11 /reg=2 @@ -2377,7 +2488,7 @@ ficomp - X87 + X87 aso rexr rexx rexb de /mod=!11 /reg=3 @@ -2392,7 +2503,7 @@ fild - X87 + X87 aso rexr rexx rexb df /mod=!11 /reg=0 @@ -2411,8 +2522,8 @@ - fncstp - X87 + fincstp + X87 d9 /mod=11 /x87=37 @@ -2420,7 +2531,7 @@ fninit - X87 + X87 db /mod=11 /x87=23 @@ -2428,7 +2539,7 @@ fiadd - X87 + X87 aso rexr rexx rexb da /mod=!11 /reg=0 @@ -2443,7 +2554,7 @@ fidivr - X87 + X87 aso rexr rexx rexb da /mod=!11 /reg=7 @@ -2458,7 +2569,7 @@ fidiv - X87 + X87 aso rexr rexx rexb da /mod=!11 /reg=6 @@ -2473,7 +2584,7 @@ fisub - X87 + X87 aso rexr rexx rexb da /mod=!11 /reg=4 @@ -2488,7 +2599,7 @@ fisubr - X87 + X87 aso rexr rexx rexb da /mod=!11 /reg=5 @@ -2503,7 +2614,7 @@ fist - X87 + X87 aso rexr rexx rexb df /mod=!11 /reg=2 @@ -2518,7 +2629,7 @@ fistp - X87 + X87 aso rexr rexx rexb df /mod=!11 /reg=3 @@ -2538,7 +2649,7 @@ fisttp - X87 + X87 aso rexr rexx rexb db /mod=!11 /reg=1 @@ -2558,7 +2669,7 @@ fld - X87 + X87 aso rexr rexx rexb db /mod=!11 /reg=5 @@ -2610,7 +2721,7 @@ fld1 - X87 + X87 d9 /mod=11 /x87=28 @@ -2618,7 +2729,7 @@ fldl2t - X87 + X87 d9 /mod=11 /x87=29 @@ -2626,15 +2737,15 @@ fldl2e - X87 + X87 d9 /mod=11 /x87=2a - fldlpi - X87 + fldpi + X87 d9 /mod=11 /x87=2b @@ -2642,7 +2753,7 @@ fldlg2 - X87 + X87 d9 /mod=11 /x87=2c @@ -2650,7 +2761,7 @@ fldln2 - X87 + X87 d9 /mod=11 /x87=2d @@ -2658,7 +2769,7 @@ fldz - X87 + X87 d9 /mod=11 /x87=2e @@ -2666,7 +2777,7 @@ fldcw - X87 + X87 aso rexr rexx rexb d9 /mod=!11 /reg=5 @@ -2676,7 +2787,7 @@ fldenv - X87 + X87 aso rexr rexx rexb d9 /mod=!11 /reg=4 @@ -2686,7 +2797,7 @@ fmul - X87 + X87 aso rexr rexx rexb dc /mod=!11 /reg=1 @@ -2765,7 +2876,7 @@ fmulp - X87 + X87 de /mod=11 /x87=08 ST0 ST0 @@ -2802,7 +2913,7 @@ fimul - X87 + X87 aso rexr rexx rexb da /mod=!11 /reg=1 @@ -2817,15 +2928,39 @@ fnop - X87 + X87 d9 /mod=11 /x87=10 + + + fndisi + X87 + + db /mod=11 /x87=21 + + + + + fneni + X87 + + db /mod=11 /x87=20 + + + + + fnsetpm + X87 + + db /mod=11 /x87=24 + + fpatan - X87 + X87 d9 /mod=11 /x87=33 @@ -2833,7 +2968,7 @@ fprem - X87 + X87 d9 /mod=11 /x87=38 @@ -2841,7 +2976,7 @@ fprem1 - X87 + X87 d9 /mod=11 /x87=35 @@ -2849,7 +2984,7 @@ fptan - X87 + X87 d9 /mod=11 /x87=32 @@ -2857,7 +2992,7 @@ frndint - X87 + X87 d9 /mod=11 /x87=3c @@ -2865,17 +3000,25 @@ frstor - X87 + X87 aso rexr rexx rexb dd /mod=!11 /reg=4 M + + + frstpm + X87 + + db /mod=11 /x87=25 + + fnsave - X87 + X87 aso rexr rexx rexb dd /mod=!11 /reg=6 @@ -2885,7 +3028,7 @@ fscale - X87 + X87 d9 /mod=11 /x87=3d @@ -2893,7 +3036,7 @@ fsin - X87 + X87 d9 /mod=11 /x87=3e @@ -2901,7 +3044,7 @@ fsincos - X87 + X87 d9 /mod=11 /x87=3b @@ -2909,7 +3052,7 @@ fsqrt - X87 + X87 d9 /mod=11 /x87=3a @@ -2917,7 +3060,7 @@ fstp - X87 + X87 aso rexr rexx rexb db /mod=!11 /reg=7 @@ -3077,7 +3220,7 @@ fst - X87 + X87 aso rexr rexx rexb d9 /mod=!11 /reg=2 @@ -3124,7 +3267,7 @@ fnstcw - X87 + X87 aso rexr rexx rexb d9 /mod=!11 /reg=7 @@ -3134,7 +3277,7 @@ fnstenv - X87 + X87 aso rexr rexx rexb d9 /mod=!11 /reg=6 @@ -3144,7 +3287,7 @@ fnstsw - X87 + X87 aso rexr rexx rexb dd /mod=!11 /reg=7 @@ -3158,7 +3301,7 @@ fsub - X87 + X87 aso rexr rexx rexb d8 /mod=!11 /reg=4 @@ -3237,7 +3380,7 @@ fsubp - X87 + X87 de /mod=11 /x87=28 ST0 ST0 @@ -3274,7 +3417,7 @@ fsubr - X87 + X87 aso rexr rexx rexb dc /mod=!11 /reg=5 @@ -3353,7 +3496,7 @@ fsubrp - X87 + X87 de /mod=11 /x87=20 ST0 ST0 @@ -3390,7 +3533,7 @@ ftst - X87 + X87 d9 /mod=11 /x87=24 @@ -3398,7 +3541,7 @@ fucom - X87 + X87 dd /mod=11 /x87=20 ST0 @@ -3435,7 +3578,7 @@ fucomp - X87 + X87 dd /mod=11 /x87=28 ST0 @@ -3472,7 +3615,7 @@ fucompp - X87 + X87 da /mod=11 /x87=29 @@ -3480,7 +3623,7 @@ fxam - X87 + X87 d9 /mod=11 /x87=25 @@ -3488,7 +3631,7 @@ fxch - X87 + X87 d9 /mod=11 /x87=08 ST0 ST0 @@ -3525,7 +3668,7 @@ fxch4 - X87 + X87 dd /mod=11 /x87=08 ST0 @@ -3562,7 +3705,7 @@ fxch7 - X87 + X87 df /mod=11 /x87=08 ST0 @@ -3601,7 +3744,7 @@ fxrstor aso rexw rexr rexx rexb - 0f ae /mod=11 /reg=1 + 0f ae /mod=!11 /reg=1 M @@ -3610,14 +3753,14 @@ fxsave aso rexw rexr rexx rexb - 0f ae /mod=11 /reg=0 + 0f ae /mod=!11 /reg=0 M - fpxtract - X87 + fxtract + X87 d9 /mod=11 /x87=34 @@ -3625,7 +3768,7 @@ fyl2x - X87 + X87 d9 /mod=11 /x87=31 @@ -3633,7 +3776,7 @@ fyl2xp1 - X87 + X87 d9 /mod=11 /x87=39 @@ -3703,13 +3846,11 @@ aso oso rexw rexr rexx rexb 69 Gv Ev Iz - sext aso oso rexw rexr rexx rexb 6b - Gv Ev Ib - sext + Gv Ev sIb @@ -3718,42 +3859,42 @@ oso 40 - eAX + R0z oso 41 - eCX + R1z oso 42 - eDX + R2z oso 43 - eBX + R3z oso 44 - eSP + R4z oso 45 - eBP + R5z oso 46 - eSI + R6z oso 47 - eDI + R7z aso oso rexw rexr rexx rexb @@ -3770,6 +3911,7 @@ insb + rep seg 6c @@ -3777,7 +3919,7 @@ insw - oso + rep oso seg 6d /o=16 @@ -3785,7 +3927,7 @@ insd - oso + rep oso seg 6d /o=32 @@ -3815,7 +3957,7 @@ into - ce + ce /m=!64 inv64 @@ -3831,11 +3973,11 @@ invept intel - sse66 0f 38 80 /m=32 + /sse=66 0f 38 80 /m=32 Gd Mo - sse66 0f 38 80 /m=64 + /sse=66 0f 38 80 /m=64 Gq Mo @@ -3861,11 +4003,11 @@ invvpid intel - sse66 0f 38 81 /m=32 + /sse=66 0f 38 81 /m=32 Gd Mo - sse66 0f 38 81 /m=64 + /sse=66 0f 38 81 /m=64 Gq Mo @@ -3904,7 +4046,7 @@ oso 0f 80 Jz - def64 depM + def64 @@ -3918,7 +4060,7 @@ oso 0f 81 Jz - def64 depM + def64 @@ -3932,7 +4074,7 @@ oso 0f 82 Jz - def64 depM + def64 @@ -3946,7 +4088,7 @@ oso 0f 83 Jz - def64 depM + def64 @@ -3960,7 +4102,7 @@ oso 0f 84 Jz - def64 depM + def64 @@ -3974,7 +4116,7 @@ oso 0f 85 Jz - def64 depM + def64 @@ -3988,7 +4130,7 @@ oso 0f 86 Jz - def64 depM + def64 @@ -4002,7 +4144,7 @@ oso 0f 87 Jz - def64 depM + def64 @@ -4016,7 +4158,7 @@ oso 0f 88 Jz - def64 depM + def64 @@ -4030,7 +4172,7 @@ oso 0f 89 Jz - def64 depM + def64 @@ -4044,7 +4186,7 @@ oso 0f 8a Jz - def64 depM + def64 @@ -4058,7 +4200,7 @@ oso 0f 8b Jz - def64 depM + def64 @@ -4072,7 +4214,7 @@ oso 0f 8c Jz - def64 depM + def64 @@ -4086,7 +4228,7 @@ oso 0f 8d Jz - def64 depM + def64 @@ -4100,7 +4242,7 @@ oso 0f 8e Jz - def64 depM + def64 @@ -4114,7 +4256,7 @@ oso 0f 8f Jz - def64 depM + def64 @@ -4151,28 +4293,28 @@ aso oso rexw rexr rexx rexb ff /reg=4 Ev - def64 depM + def64 aso oso rexw rexr rexx rexb ff /reg=5 - Ep + Fv oso e9 Jz - def64 depM - cast + def64 - ea - Ap - inv64 + oso + ea /m=!64 + Av eb Jb + def64 @@ -4192,20 +4334,11 @@ - - lddqu - - aso rexr rexx rexb - ssef2 0f f0 - V M - - - ldmxcsr aso rexw rexr rexx rexb - 0f ae /reg=2 /mod=11 + 0f ae /reg=2 /mod=!11 Md @@ -4214,9 +4347,8 @@ lds aso oso - c5 + c5 /vex=none /m=!64 Gv M - inv64 @@ -4233,9 +4365,8 @@ les aso oso - c4 + c4 /m=!64 Gv M - inv64 @@ -4271,7 +4402,7 @@ aso oso rexw rexr rexx rexb 0f b2 - Gz M + Gv M @@ -4335,6 +4466,11 @@ 0f 01 /reg=6 /mod=!11 Ew + + aso rexr rexx rexb + 0f 01 /reg=6 /mod=11 + Ew + @@ -4347,7 +4483,7 @@ lodsb - seg + rep seg ac @@ -4355,7 +4491,7 @@ lodsw - seg oso rexw + rep seg oso rexw ad /o=16 @@ -4363,7 +4499,7 @@ lodsd - seg oso rexw + rep seg oso rexw ad /o=32 @@ -4371,13 +4507,13 @@ lodsq - seg oso rexw + rep seg oso rexw ad /o=64 - loopnz + loopne e0 Jb @@ -4422,26 +4558,28 @@ maskmovq aso rexr rexx rexb - 0f f7 - P PR + 0f f7 /mod=11 + P N maxpd - aso rexr rexx rexb - sse66 0f 5f - V W + aso rexr rexx rexb vexl + /sse=66 0f 5f + V H W + sse2 avx maxps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 5f - V W + V H W + sse avx @@ -4449,8 +4587,9 @@ maxsd aso rexr rexx rexb - ssef2 0f 5f - V W + /sse=f2 0f 5f + V H W + sse2 avx @@ -4458,8 +4597,9 @@ maxss aso rexr rexx rexb - ssef3 0f 5f - V W + /sse=f3 0f 5f + V H W + sse avx @@ -4494,9 +4634,10 @@ minpd - aso rexr rexx rexb - sse66 0f 5d - V W + aso rexr rexx rexb vexl + /sse=66 0f 5d + V H W + sse2 avx @@ -4505,7 +4646,8 @@ aso rexr rexx rexb 0f 5d - V W + V H W + sse2 avx @@ -4513,8 +4655,9 @@ minsd aso rexr rexx rexb - ssef2 0f 5d - V W + /sse=f2 0f 5d + V H MqU + sse2 avx @@ -4522,8 +4665,9 @@ minss aso rexr rexx rexb - ssef3 0f 5d - V W + /sse=f3 0f 5d + V H MdU + sse avx @@ -4551,7 +4695,7 @@ aso oso rexw rexr rexx rexb c7 /reg=0 - Ev Iz + Ev sIz aso rexr rexx rexb @@ -4574,14 +4718,14 @@ Gv Ev - aso oso rexr rexx rexb + aso oso rexw rexr rexx rexb 8c - Ev S + MwRv S - aso oso rexr rexx rexb + aso oso rexw rexr rexx rexb 8e - S Ev + S MwRv a0 @@ -4604,100 +4748,100 @@ rexb b0 - ALr8b Ib + R0b Ib rexb b1 - CLr9b Ib + R1b Ib rexb b2 - DLr10b Ib + R2b Ib rexb b3 - BLr11b Ib + R3b Ib rexb b4 - AHr12b Ib + R4b Ib rexb b5 - CHr13b Ib + R5b Ib rexb b6 - DHr14b Ib + R6b Ib rexb b7 - BHr15b Ib + R7b Ib oso rexw rexb b8 - rAXr8 Iv + R0v Iv oso rexw rexb b9 - rCXr9 Iv + R1v Iv oso rexw rexb ba - rDXr10 Iv + R2v Iv oso rexw rexb bb - rBXr11 Iv + R3v Iv oso rexw rexb bc - rSPr12 Iv + R4v Iv oso rexw rexb bd - rBPr13 Iv + R5v Iv oso rexw rexb be - rSIr14 Iv + R6v Iv oso rexw rexb bf - rDIr15 Iv + R7v Iv - rexr + rexr rexw rexb 0f 20 R C - rexr + rexr rexw rexb 0f 21 R D - rexr + rexr rexw rexb 0f 22 C R - rexr + rexr rexw rexb 0f 23 D R @@ -4706,28 +4850,32 @@ movapd - aso rexr rexx rexb - sse66 0f 28 + aso rexr rexx rexb vexl + /sse=66 0f 28 V W + sse2 avx - aso rexr rexx rexb - sse66 0f 29 + aso rexr rexx rexb vexl + /sse=66 0f 29 W V + sse2 avx movaps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 28 V W + sse avx - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 29 W V + sse avx @@ -4735,23 +4883,52 @@ movd aso rexw rexr rexx rexb - sse66 0f 6e - V Ex + 0f 6e /o=16 + P Ey + mmx - aso rexr rexx rexb - 0f 6e - P Ex + aso rexw rexr rexx rexb + 0f 6e /o=32 + P Ey + mmx + aso rexw rexr rexx rexb - sse66 0f 7e - Ex V + /sse=66 0f 6e /o=16 + V Ey + sse2 avx - aso rexr rexx rexb - 0f 7e - Ex P + aso rexw rexr rexx rexb + /sse=66 0f 6e /o=32 + V Ey + sse2 avx + + + aso rexw rexr rexx rexb + 0f 7e /o=16 + Ey P + mmx + + + aso rexw rexr rexx rexb + 0f 7e /o=32 + Ey P + mmx + + + aso rexw rexr rexx rexb + /sse=66 0f 7e /o=16 + Ey V + sse2 avx + + + aso rexw rexr rexx rexb + /sse=66 0f 7e /o=32 + Ey V + sse2 avx @@ -4759,13 +4936,15 @@ movhpd aso rexr rexx rexb - sse66 0f 16 /mod=!11 - V M + /sse=66 0f 16 /mod=!11 + V H M + sse2 avx aso rexr rexx rexb - sse66 0f 17 + /sse=66 0f 17 M V + sse2 avx @@ -4774,12 +4953,14 @@ aso rexr rexx rexb 0f 16 /mod=!11 - V M + V H M + sse avx aso rexr rexx rexb 0f 17 M V + sse avx @@ -4788,7 +4969,8 @@ aso rexr rexx rexb 0f 16 /mod=11 - V VR + V H U + sse avx @@ -4796,14 +4978,15 @@ movlpd aso rexr rexx rexb - sse66 0f 12 /mod=!11 + /sse=66 0f 12 /mod=!11 V M aso rexr rexx rexb - sse66 0f 13 + /sse=66 0f 13 M V + sse2 avx @@ -4818,6 +5001,7 @@ 0f 13 M V + sse avx @@ -4825,16 +5009,18 @@ aso rexr rexx rexb 0f 12 /mod=11 - V VR + V U + sse avx movmskpd - oso rexr rexb - sse66 0f 50 - Gd VR + oso rexr rexb vexl + /sse=66 0f 50 + Gd U + sse2 avx @@ -4843,16 +5029,18 @@ oso rexr rexb 0f 50 - Gd VR + Gd U + sse2 avx movntdq - aso rexr rexx rexb - sse66 0f e7 + aso rexr rexx rexb vexl + /sse=66 0f e7 M V + sse2 avx @@ -4868,24 +5056,27 @@ movntpd - aso rexr rexx rexb - sse66 0f 2b + aso rexr rexx rexb vexl + /sse=66 0f 2b M V + sse2 avx movntps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 2b M V + sse2 avx movntq + aso rexr rexx rexb 0f e7 M P @@ -4894,31 +5085,59 @@ movq - aso rexr rexx rexb - 0f 6f - P Q + aso rexw rexr rexx rexb + 0f 6e /o=64 + P Eq + mmx - aso rexr rexx rexb - sse66 0f d6 - W V + aso rexw rexr rexx rexb + /sse=66 0f 6e /o=64 + V Eq + sse2 avx - aso rexr rexx rexb - ssef3 0f 7e + aso rexw rexr rexx rexb + 0f 7e /o=64 + Eq P + mmx + + + aso rexw rexr rexx rexb + /sse=66 0f 7e /o=64 + Eq V + sse2 avx + + + aso rexw rexr rexx rexb + /sse=f3 0f 7e V W + sse2 avx - aso rexr rexx rexb + aso rexw rexr rexx rexb + /sse=66 0f d6 + W V + sse2 avx + + + aso rexw rexr rexx rexb + 0f 6f + P Q + mmx + + + aso rexw rexr rexx rexb 0f 7f Q P + mmx movsb - seg + rep seg a4 @@ -4926,7 +5145,7 @@ movsw - seg oso rexw + rep seg oso rexw a5 /o=16 @@ -4934,25 +5153,27 @@ movsd - seg oso rexw + rep seg oso rexw a5 /o=32 aso rexr rexx rexb - ssef2 0f 10 - V W + /sse=f2 0f 10 + V MqU + sse2 aso rexr rexx rexb - ssef2 0f 11 + /sse=f2 0f 11 W V + sse2 movsq - seg oso rexw + rep seg oso rexw a5 /o=64 @@ -4961,13 +5182,15 @@ movss aso rexr rexx rexb - ssef3 0f 10 - V W + /sse=f3 0f 10 + V MdU + sse aso rexr rexx rexb - ssef3 0f 11 + /sse=f3 0f 11 W V + sse @@ -4981,35 +5204,39 @@ aso oso rexw rexr rexx rexb 0f bf - Gv Ew + Gy Ew movupd - aso rexr rexx rexb - sse66 0f 10 + aso rexr rexx rexb vexl + /sse=66 0f 10 V W + sse2 avx - aso rexr rexx rexb - sse66 0f 11 + aso rexr rexx rexb vexl + /sse=66 0f 11 W V + sse2 avx movups - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 10 V W + sse2 avx - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 11 W V + sse2 avx @@ -5023,7 +5250,7 @@ aso oso rexw rexr rexx rexb 0f b7 - Gv Ew + Gy Ew @@ -5044,18 +5271,20 @@ mulpd - aso rexr rexx rexb - sse66 0f 59 - V W + aso rexr rexx rexb vexl + /sse=66 0f 59 + V H W + sse2 avx mulps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 59 - V W + V H W + sse2 avx @@ -5063,8 +5292,9 @@ mulsd aso rexr rexx rexb - ssef2 0f 59 - V W + /sse=f2 0f 59 + V H W + sse2 avx @@ -5072,8 +5302,9 @@ mulss aso rexr rexx rexb - ssef3 0f 59 - V W + /sse=f3 0f 59 + V H W + sse avx @@ -5100,9 +5331,6 @@ nop - - 90 - aso rexr rexx rexb 0f 19 @@ -5183,8 +5411,7 @@ oso rexw 0d - rAX Iz - sext + rAX sIz aso rexr rexx rexb @@ -5194,38 +5421,37 @@ aso oso rexw rexr rexx rexb 81 /reg=1 - Ev Iz - sext + Ev sIz aso rexr rexx rexb - 82 /reg=1 + 82 /reg=1 /m=!64 Eb Ib - inv64 aso oso rexw rexr rexx rexb 83 /reg=1 - Ev Ib - sext + Ev sIb orpd - aso rexr rexx rexb - sse66 0f 56 - V W + aso rexr rexx rexb vexl + /sse=66 0f 56 + V H W + sse2 avx orps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 56 - V W + V H W + sse avx @@ -5254,6 +5480,7 @@ outsb + rep seg 6e @@ -5261,7 +5488,7 @@ outsw - oso + rep oso seg 6f /o=16 @@ -5269,72 +5496,72 @@ outsd - oso + rep oso seg 6f /o=32 - - outsq - - oso - 6f /o=64 - - - packsswb - aso rexr rexx rexb - sse66 0f 63 - V W + aso rexr rexx rexb vexl + /sse=66 0f 63 + V H W + sse2 avx aso rexr rexx rexb 0f 63 P Q + mmx packssdw - aso rexr rexx rexb - sse66 0f 6b - V W + aso rexr rexx rexb vexl + /sse=66 0f 6b + V H W + sse2 avx aso rexr rexx rexb 0f 6b P Q + mmx packuswb - aso rexr rexx rexb - sse66 0f 67 - V W + aso rexr rexx rexb vexl + /sse=66 0f 67 + V H W + sse2 avx aso rexr rexx rexb 0f 67 P Q + mmx paddb - aso rexr rexx rexb - sse66 0f fc - V W + aso rexr rexx rexb vexl + /sse=66 0f fc + V H W + sse2 avx aso rexr rexx rexb 0f fc P Q + mmx @@ -5344,11 +5571,13 @@ aso rexr rexx rexb 0f fd P Q + mmx - aso rexr rexx rexb - sse66 0f fd - V W + aso rexr rexx rexb vexl + /sse=66 0f fd + V H W + sse2 avx @@ -5358,11 +5587,13 @@ aso rexr rexx rexb 0f fe P Q + mmx - aso rexr rexx rexb - sse66 0f fe - V W + aso rexr rexx rexb vexl + /sse=66 0f fe + V H W + sse2 avx @@ -5376,8 +5607,9 @@ aso rexr rexx rexb - sse66 0f ec - V W + /sse=66 0f ec + V H W + sse2 avx @@ -5390,8 +5622,9 @@ aso rexr rexx rexb - sse66 0f ed - V W + /sse=66 0f ed + V H W + sse2 avx @@ -5404,8 +5637,9 @@ aso rexr rexx rexb - sse66 0f dc - V W + /sse=66 0f dc + V H W + sse2 avx @@ -5418,8 +5652,9 @@ aso rexr rexx rexb - sse66 0f dd - V W + /sse=66 0f dd + V H W + sse2 avx @@ -5427,8 +5662,9 @@ pand aso rexr rexx rexb - sse66 0f db - V W + /sse=66 0f db + V H W + sse2 avx aso rexr rexx rexb @@ -5441,8 +5677,9 @@ pandn aso rexr rexx rexb - sse66 0f df - V W + /sse=66 0f df + V H W + sse2 avx aso rexr rexx rexb @@ -5455,8 +5692,9 @@ pavgb aso rexr rexx rexb - sse66 0f e0 - V W + /sse=66 0f e0 + V H W + sse2 avx aso rexr rexx rexb @@ -5469,8 +5707,9 @@ pavgw aso rexr rexx rexb - sse66 0f e3 - V W + /sse=66 0f e3 + V H W + sse2 avx aso rexr rexx rexb @@ -5488,8 +5727,9 @@ aso rexr rexx rexb - sse66 0f 74 - V W + /sse=66 0f 74 + V H W + sse2 avx @@ -5502,8 +5742,9 @@ aso rexr rexx rexb - sse66 0f 75 - V W + /sse=66 0f 75 + V H W + sse2 avx @@ -5516,8 +5757,9 @@ aso rexr rexx rexb - sse66 0f 76 - V W + /sse=66 0f 76 + V H W + sse2 avx @@ -5525,8 +5767,9 @@ pcmpgtb aso rexr rexx rexb - sse66 0f 64 - V W + /sse=66 0f 64 + V H W + sse2 avx aso rexr rexx rexb @@ -5539,8 +5782,9 @@ pcmpgtw aso rexr rexx rexb - sse66 0f 65 - V W + /sse=66 0f 65 + V H W + sse2 avx aso rexr rexx rexb @@ -5553,8 +5797,9 @@ pcmpgtd aso rexr rexx rexb - sse66 0f 66 - V W + /sse=66 0f 66 + V H W + sse2 avx aso rexr rexx rexb @@ -5566,24 +5811,27 @@ pextrb - aso rexr rexb - sse66 0f 3a 14 + aso rexx rexr rexb + /sse=66 0f 3a 14 /vexw=0 MbRv V Ib def64 + sse4.1 avx pextrd - aso rexr rexw rexb - sse66 0f 3a 16 /o=16 - Ev V Ib + aso rexr rexx rexw rexb + /sse=66 0f 3a 16 /o=16 /vexw=0 + Ed V Ib + sse4.1 avx - aso rexr rexw rexb - sse66 0f 3a 16 /o=32 - Ev V Ib + aso rexr rexx rexw rexb + /sse=66 0f 3a 16 /o=32 /vexw=0 + Ed V Ib + sse4.1 avx @@ -5591,62 +5839,150 @@ pextrq aso rexr rexw rexb - sse66 0f 3a 16 /o=64 - Ev V Ib + /sse=66 0f 3a 16 /o=64 /vexw=1 + Eq V Ib def64 + sse4.1 avx pextrw - aso rexr rexb - sse66 0f c5 - Gd VR Ib + aso rexw rexr rexb + /sse=66 0f c5 + Gd U Ib + sse avx - aso oso rexw rexr rexx rexb + aso rexw rexr rexx rexb 0f c5 - Gd PR Ib + Gd N Ib + + + aso rexw rexx rexr rexb + /sse=66 0f 3a 15 + MwRd V Ib + sse4.1 avx + + + + + pinsrb + + aso rexw rexr rexx rexb + /sse=66 0f 3a 20 + V MbRd Ib + sse4.1 pinsrw - aso oso rexw rexr rexx rexb + aso rexw rexr rexx rexb 0f c4 - P Ew Ib + P MwRy Ib + def64 aso rexw rexr rexx rexb - sse66 0f c4 - V Ew Ib + /sse=66 0f c4 + V MwRy Ib + def64 + sse2 avx - pmaddwd + pinsrd - aso rexr rexx rexb - 0f f5 - P Q + aso rexw rexr rexx rexb + /sse=66 0f 3a 22 /o=16 + V Ed Ib + sse4.1 + - aso rexr rexx rexb - sse66 0f f5 - V W + aso rexw rexr rexx rexb + /sse=66 0f 3a 22 /o=32 + V Ed Ib + sse4.1 - pmaxsw + pinsrq - aso rexr rexx rexb - sse66 0f ee - V W + aso oso rexw rexr rexx rexb + /sse=66 0f 3a 22 /o=64 + V Eq Ib + sse4.1 - + + + + vpinsrb + + aso rexw rexr rexx rexb + /vex=66_0f3a 20 /vexw=0 /vexl=0 + V H MbRd Ib + avx + + + + + vpinsrd + + aso oso rexw rexr rexx rexb + /vex=66_0f3a 22 /m=!64 /vexw=0 /vexl=0 + V H Ed Ib + avx + + + aso oso rexw rexr rexx rexb + /vex=66_0f3a 22 /m=64 /vexw=0 /vexl=0 + V H Ed Ib + avx + + + + + + vpinsrq + + aso oso rexw rexr rexx rexb + /vex=66_0f3a 22 /m=64 /vexw=1 /vexl=0 + V H Eq Ib + avx + + + + + + pmaddwd + + aso rexr rexx rexb + 0f f5 + P Q + + + aso rexr rexx rexb + /sse=66 0f f5 + V H W + sse4.1 avx + + + + + pmaxsw + + aso rexr rexx rexb + /sse=66 0f ee + V H W + sse4.1 avx + + aso rexr rexx rexb 0f ee P Q @@ -5662,8 +5998,9 @@ aso rexr rexx rexb - sse66 0f de - V W + /sse=66 0f de + V H W + sse2 avx @@ -5671,8 +6008,9 @@ pminsw aso rexr rexx rexb - sse66 0f ea - V W + /sse=66 0f ea + V H W + sse2 avx aso rexr rexx rexb @@ -5685,8 +6023,9 @@ pminub aso rexr rexx rexb - sse66 0f da - V W + /sse=66 0f da + V H W + sse2 avx aso rexr rexx rexb @@ -5698,14 +6037,15 @@ pmovmskb - rexr rexb - sse66 0f d7 - Gd VR + oso rexr rexw rexb + /sse=66 0f d7 /vexl=0 + Gd U + sse2 avx - oso rexr rexb + oso rexr rexw rexb 0f d7 - Gd PR + Gd N @@ -5718,8 +6058,9 @@ aso rexr rexx rexb - sse66 0f e4 - V W + /sse=66 0f e4 + V H W + sse2 avx @@ -5727,8 +6068,9 @@ pmulhw aso rexr rexx rexb - sse66 0f e5 - V W + /sse=66 0f e5 + V H W + sse2 avx aso rexr rexx rexb @@ -5746,25 +6088,26 @@ aso rexr rexx rexb - sse66 0f d5 - V W + /sse=66 0f d5 + V H W + sse2 avx pop - 07 + 07 /m=!64 ES inv64 - 17 + 17 /m=!64 SS inv64 - 1f + 1f /m=!64 DS inv64 @@ -5779,56 +6122,56 @@ oso rexb 58 - rAXr8 - def64 depM + R0v + def64 oso rexb 59 - rCXr9 - def64 depM + R1v + def64 oso rexb 5a - rDXr10 - def64 depM + R2v + def64 oso rexb 5b - rBXr11 - def64 depM + R3v + def64 oso rexb 5c - rSPr12 - def64 depM + R4v + def64 oso rexb 5d - rBPr13 - def64 depM + R5v + def64 oso rexb 5e - rSIr14 - def64 depM + R6v + def64 oso rexb 5f - rDIr15 - def64 depM + R7v + def64 aso oso rexw rexr rexx rexb 8f /reg=0 Ev - def64 depM + def64 @@ -5836,7 +6179,7 @@ popa oso - 61 /o=16 + 61 /o=16 /m=!64 inv64 @@ -5845,7 +6188,7 @@ popad oso - 61 /o=32 + 61 /o=32 /m=!64 inv64 @@ -5854,13 +6197,7 @@ popfw oso - 9d /m=32 /o=16 - def64 depM - - - oso - 9d /m=16 /o=16 - def64 depM + 9d /m=!64 /o=16 @@ -5868,22 +6205,21 @@ popfd oso - 9d /m=16 /o=32 - def64 depM - - - oso - 9d /m=32 /o=32 - def64 depM + 9d /m=!64 /o=32 popfq + + oso + 9d /m=64 /o=32 + def64 + oso 9d /m=64 /o=64 - def64 depM + def64 @@ -5891,8 +6227,9 @@ por aso rexr rexx rexb - sse66 0f eb - V W + /sse=66 0f eb + V H W + sse2 avx aso rexr rexx rexb @@ -5985,8 +6322,9 @@ psadbw aso rexr rexx rexb - sse66 0f f6 - V W + /sse=66 0f f6 + V H W + sse2 avx aso rexr rexx rexb @@ -6004,12 +6342,13 @@ - + psllw aso rexr rexx rexb - sse66 0f f1 + /sse=66 0f f1 V W + sse2 aso rexr rexx rexb @@ -6018,12 +6357,13 @@ rexb - sse66 0f 71 /reg=6 - VR Ib + /sse=66 0f 71 /reg=6 + U Ib + sse2 0f 71 /reg=6 - PR Ib + N Ib @@ -6031,8 +6371,9 @@ pslld aso rexr rexx rexb - sse66 0f f2 + /sse=66 0f f2 V W + sse2 aso rexr rexx rexb @@ -6041,12 +6382,13 @@ rexb - sse66 0f 72 /reg=6 - VR Ib + /sse=66 0f 72 /reg=6 + U Ib + sse2 0f 72 /reg=6 - PR Ib + N Ib @@ -6054,8 +6396,9 @@ psllq aso rexr rexx rexb - sse66 0f f3 + /sse=66 0f f3 V W + sse2 aso rexr rexx rexb @@ -6064,12 +6407,13 @@ rexb - sse66 0f 73 /reg=6 - VR Ib + /sse=66 0f 73 /reg=6 + U Ib + sse2 0f 73 /reg=6 - PR Ib + N Ib @@ -6082,17 +6426,19 @@ aso rexr rexx rexb - sse66 0f e1 - V W + /sse=66 0f e1 + V H W + sse2 avx rexb - sse66 0f 71 /reg=4 - VR Ib + /sse=66 0f 71 /reg=4 + H U Ib + sse2 avx 0f 71 /reg=4 - PR Ib + N Ib @@ -6100,12 +6446,13 @@ psrad 0f 72 /reg=4 - PR Ib + N Ib aso rexr rexx rexb - sse66 0f e2 - V W + /sse=66 0f e2 + V H W + sse2 avx aso rexr rexx rexb @@ -6114,8 +6461,9 @@ rexb - sse66 0f 72 /reg=4 - VR Ib + /sse=66 0f 72 /reg=4 + H U Ib + sse2 avx @@ -6123,7 +6471,7 @@ psrlw 0f 71 /reg=2 - PR Ib + N Ib aso rexr rexx rexb @@ -6132,13 +6480,15 @@ aso rexr rexx rexb - sse66 0f d1 - V W + /sse=66 0f d1 + V H W + sse2 avx rexb - sse66 0f 71 /reg=2 - VR Ib + /sse=66 0f 71 /reg=2 + H U Ib + sse2 avx @@ -6146,7 +6496,7 @@ psrld 0f 72 /reg=2 - PR Ib + N Ib aso rexr rexx rexb @@ -6155,13 +6505,15 @@ aso rexr rexx rexb - sse66 0f d2 - V W + /sse=66 0f d2 + V H W + sse2 avx rexb - sse66 0f 72 /reg=2 - VR Ib + /sse=66 0f 72 /reg=2 + H U Ib + sse2 avx @@ -6169,7 +6521,7 @@ psrlq 0f 73 /reg=2 - PR Ib + N Ib aso rexr rexx rexb @@ -6178,13 +6530,15 @@ aso rexr rexx rexb - sse66 0f d3 - V W + /sse=66 0f d3 + V H W + sse2 avx rexb - sse66 0f 73 /reg=2 - VR Ib + /sse=66 0f 73 /reg=2 + H U Ib + sse2 avx @@ -6192,8 +6546,9 @@ psubb aso rexr rexx rexb - sse66 0f f8 - V W + /sse=66 0f f8 + V H W + sse2 avx aso rexr rexx rexb @@ -6206,8 +6561,9 @@ psubw aso rexr rexx rexb - sse66 0f f9 - V W + /sse=66 0f f9 + V H W + sse2 avx aso rexr rexx rexb @@ -6225,8 +6581,9 @@ aso rexr rexx rexb - sse66 0f fa - V W + /sse=66 0f fa + V H W + sse2 avx @@ -6239,8 +6596,9 @@ aso rexr rexx rexb - sse66 0f e8 - V W + /sse=66 0f e8 + V H W + sse2 avx @@ -6253,8 +6611,9 @@ aso rexr rexx rexb - sse66 0f e9 - V W + /sse=66 0f e9 + V H W + sse2 avx @@ -6267,8 +6626,9 @@ aso rexr rexx rexb - sse66 0f d8 - V W + /sse=66 0f d8 + V H W + sse2 avx @@ -6281,8 +6641,9 @@ aso rexr rexx rexb - sse66 0f d9 - V W + /sse=66 0f d9 + V H W + sse2 avx @@ -6290,8 +6651,9 @@ punpckhbw aso rexr rexx rexb - sse66 0f 68 - V W + /sse=66 0f 68 + V H W + sse2 avx aso rexr rexx rexb @@ -6304,8 +6666,9 @@ punpckhwd aso rexr rexx rexb - sse66 0f 69 - V W + /sse=66 0f 69 + V H W + sse2 avx aso rexr rexx rexb @@ -6318,8 +6681,9 @@ punpckhdq aso rexr rexx rexb - sse66 0f 6a - V W + /sse=66 0f 6a + V H W + sse2 avx aso rexr rexx rexb @@ -6332,8 +6696,9 @@ punpcklbw aso rexr rexx rexb - sse66 0f 60 - V W + /sse=66 0f 60 + V H W + sse2 avx aso rexr rexx rexb @@ -6346,8 +6711,9 @@ punpcklwd aso rexr rexx rexb - sse66 0f 61 - V W + /sse=66 0f 61 + V H W + sse2 avx aso rexr rexx rexb @@ -6360,8 +6726,9 @@ punpckldq aso rexr rexx rexb - sse66 0f 62 - V W + /sse=66 0f 62 + V H W + sse2 avx aso rexr rexx rexb @@ -6373,6 +6740,7 @@ pi2fw + aso rexr rexx rexb 0f 0f /3dnow=0c P Q @@ -6381,6 +6749,7 @@ pi2fd + aso rexr rexx rexb 0f 0f /3dnow=0d P Q @@ -6389,6 +6758,7 @@ pf2iw + aso rexr rexx rexb 0f 0f /3dnow=1c P Q @@ -6397,6 +6767,7 @@ pf2id + aso rexr rexx rexb 0f 0f /3dnow=1d P Q @@ -6405,6 +6776,7 @@ pfnacc + aso rexr rexx rexb 0f 0f /3dnow=8a P Q @@ -6413,6 +6785,7 @@ pfpnacc + aso rexr rexx rexb 0f 0f /3dnow=8e P Q @@ -6421,6 +6794,7 @@ pfcmpge + aso rexr rexx rexb 0f 0f /3dnow=90 P Q @@ -6429,6 +6803,7 @@ pfmin + aso rexr rexx rexb 0f 0f /3dnow=94 P Q @@ -6437,6 +6812,7 @@ pfrcp + aso rexr rexx rexb 0f 0f /3dnow=96 P Q @@ -6445,6 +6821,7 @@ pfrsqrt + aso rexr rexx rexb 0f 0f /3dnow=97 P Q @@ -6453,6 +6830,7 @@ pfsub + aso rexr rexx rexb 0f 0f /3dnow=9a P Q @@ -6461,6 +6839,7 @@ pfadd + aso rexr rexx rexb 0f 0f /3dnow=9e P Q @@ -6469,6 +6848,7 @@ pfcmpgt + aso rexr rexx rexb 0f 0f /3dnow=a0 P Q @@ -6477,6 +6857,7 @@ pfmax + aso rexr rexx rexb 0f 0f /3dnow=a4 P Q @@ -6485,6 +6866,7 @@ pfrcpit1 + aso rexr rexx rexb 0f 0f /3dnow=a6 P Q @@ -6493,6 +6875,7 @@ pfrsqit1 + aso rexr rexx rexb 0f 0f /3dnow=a7 P Q @@ -6501,6 +6884,7 @@ pfsubr + aso rexr rexx rexb 0f 0f /3dnow=aa P Q @@ -6509,6 +6893,7 @@ pfacc + aso rexr rexx rexb 0f 0f /3dnow=ae P Q @@ -6517,6 +6902,7 @@ pfcmpeq + aso rexr rexx rexb 0f 0f /3dnow=b0 P Q @@ -6525,6 +6911,7 @@ pfmul + aso rexr rexx rexb 0f 0f /3dnow=b4 P Q @@ -6533,6 +6920,7 @@ pfrcpit2 + aso rexr rexx rexb 0f 0f /3dnow=b6 P Q @@ -6541,6 +6929,7 @@ pmulhrw + aso rexr rexx rexb 0f 0f /3dnow=b7 P Q @@ -6549,6 +6938,7 @@ pswapd + aso rexr rexx rexb 0f 0f /3dnow=bb P Q @@ -6557,6 +6947,7 @@ pavgusb + aso rexr rexx rexb 0f 0f /3dnow=bf P Q @@ -6565,22 +6956,22 @@ push - 06 + 06 /m=!64 ES inv64 - 0e + 0e /m=!64 CS inv64 - 16 + 16 /m=!64 SS inv64 - 1e + 1e /m=!64 DS inv64 @@ -6595,56 +6986,56 @@ oso rexb 50 - rAXr8 - def64 depM + R0v + def64 oso rexb 51 - rCXr9 - def64 depM + R1v + def64 oso rexb 52 - rDXr10 - def64 depM + R2v + def64 oso rexb 53 - rBXr11 - def64 depM + R3v + def64 oso rexb 54 - rSPr12 - def64 depM + R4v + def64 oso rexb 55 - rBPr13 - def64 depM + R5v + def64 oso rexb 56 - rSIr14 - def64 depM + R6v + def64 oso rexb 57 - rDIr15 - def64 depM + R7v + def64 oso 68 - Iz - cast + sIz + def64 aso oso rexw rexr rexx rexb @@ -6653,9 +7044,10 @@ def64 + oso 6a - Ib - sext + sIb + def64 @@ -6663,7 +7055,7 @@ pusha oso - 60 /o=16 + 60 /o=16 /m=!64 inv64 @@ -6672,7 +7064,7 @@ pushad oso - 60 /o=32 + 60 /o=32 /m=!64 inv64 @@ -6681,13 +7073,7 @@ pushfw oso - 9c /m=32 /o=16 - def64 - - - oso - 9c /m=16 /o=16 - def64 + 9c /m=!64 /o=16 oso rexw @@ -6700,13 +7086,7 @@ pushfd oso - 9c /m=16 /o=32 - def64 - - - oso - 9c /m=32 /o=32 - def64 + 9c /m=!64 /o=32 @@ -6728,8 +7108,9 @@ pxor aso rexr rexx rexb - sse66 0f ef - V W + /sse=66 0f ef + V H W + sse2 avx aso rexr rexx rexb @@ -6759,13 +7140,11 @@ aso rexw rexr rexx rexb d2 /reg=2 Eb CL - cast aso oso rexw rexr rexx rexb d3 /reg=2 Ev CL - cast aso oso rexw rexr rexx rexb @@ -6800,13 +7179,11 @@ aso rexw rexr rexx rexb d2 /reg=3 Eb CL - cast aso oso rexw rexr rexx rexb d3 /reg=3 Ev CL - cast @@ -6831,13 +7208,11 @@ aso rexw rexr rexx rexb d2 /reg=0 Eb CL - cast aso oso rexw rexr rexx rexb d3 /reg=0 Ev CL - cast aso oso rexw rexr rexx rexb @@ -6872,22 +7247,21 @@ aso rexw rexr rexx rexb d2 /reg=1 Eb CL - cast aso oso rexw rexr rexx rexb d3 /reg=1 Ev CL - cast rcpps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 53 V W + sse avx @@ -6895,8 +7269,9 @@ rcpss aso rexr rexx rexb - ssef3 0f 53 + /sse=f3 0f 53 V W + sse avx @@ -6975,9 +7350,10 @@ rsqrtps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 52 V W + sse avx @@ -6985,8 +7361,9 @@ rsqrtss aso rexr rexx rexb - ssef3 0f 52 + /sse=f3 0f 52 V W + sse avx @@ -7004,7 +7381,7 @@ salc - d6 + d6 /m=!64 inv64 @@ -7035,13 +7412,11 @@ aso rexw rexr rexx rexb d2 /reg=7 Eb CL - cast aso oso rexw rexr rexx rexb d3 /reg=7 Ev CL - cast @@ -7066,13 +7441,11 @@ aso rexw rexr rexx rexb d2 /reg=6 Eb CL - cast aso oso rexw rexr rexx rexb d3 /reg=6 Ev CL - cast aso oso rexw rexr rexx rexb @@ -7083,7 +7456,6 @@ aso rexr rexx rexb d2 /reg=4 Eb CL - cast aso oso rexw rexr rexx rexb @@ -7123,7 +7495,6 @@ aso rexw rexr rexx rexb d2 /reg=5 Eb CL - cast aso oso rexw rexr rexx rexb @@ -7144,7 +7515,6 @@ aso oso rexw rexr rexx rexb d3 /reg=5 Ev CL - cast @@ -7177,8 +7547,7 @@ oso rexw 1d - rAX Iz - sext + rAX sIz aso rexr rexx rexb @@ -7188,26 +7557,25 @@ aso oso rexw rexr rexx rexb 81 /reg=3 - Ev Iz - sext + Ev sIz aso rexr rexx rexb - 82 /reg=3 + 82 /reg=3 /m=!64 Eb Ib inv64 aso oso rexw rexr rexx rexb 83 /reg=3 - Ev Ib - sext + Ev sIb scasb + repz ae @@ -7215,7 +7583,7 @@ scasw - oso rexw + repz oso rexw af /o=16 @@ -7223,7 +7591,7 @@ scasd - oso rexw + repz oso rexw af /o=32 @@ -7231,7 +7599,7 @@ scasq - oso rexw + repz oso rexw af /o=64 @@ -7264,7 +7632,7 @@ - setnb + setae aso rexr rexx rexb 0f 93 @@ -7448,9 +7816,10 @@ shufpd - aso rexr rexx rexb - sse66 0f c6 - V W Ib + aso rexr rexx rexb vexl + /sse=66 0f c6 + V H W Ib + sse2 avx @@ -7459,7 +7828,8 @@ aso rexr rexx rexb 0f c6 - V W Ib + V H W Ib + sse2 avx @@ -7475,7 +7845,7 @@ sldt - aso oso rexr rexx rexb + aso oso rexr rexw rexx rexb 0f 00 /reg=0 MwRv @@ -7484,18 +7854,24 @@ smsw - aso rexr rexx rexb + aso oso rexr rexw rexx rexb 0f 01 /reg=4 /mod=!11 - M + MwRv + + + aso oso rexr rexw rexx rexb + 0f 01 /reg=4 /mod=11 + MwRv sqrtps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 51 V W + sse avx @@ -7503,8 +7879,9 @@ sqrtpd aso rexr rexx rexb - sse66 0f 51 + /sse=66 0f 51 V W + sse2 avx @@ -7512,8 +7889,9 @@ sqrtsd aso rexr rexx rexb - ssef2 0f 51 - V W + /sse=f2 0f 51 + V H W + sse2 avx @@ -7521,8 +7899,9 @@ sqrtss aso rexr rexx rexb - ssef3 0f 51 - V W + /sse=f3 0f 51 + V H W + sse avx @@ -7567,15 +7946,16 @@ stmxcsr aso rexw rexr rexx rexb - 0f ae /mod=11 /reg=3 + 0f ae /mod=!11 /reg=3 Md + sse avx stosb - seg + rep seg aa @@ -7583,7 +7963,7 @@ stosw - seg oso rexw + rep seg oso rexw ab /o=16 @@ -7591,7 +7971,7 @@ stosd - seg oso rexw + rep seg oso rexw ab /o=32 @@ -7599,7 +7979,7 @@ stosq - seg oso rexw + rep seg oso rexw ab /o=64 @@ -7607,9 +7987,9 @@ str - aso oso rexr rexx rexb + aso oso rexr rexw rexx rexb 0f 00 /reg=1 - Ev + MwRv @@ -7642,8 +8022,7 @@ oso rexw 2d - rAX Iz - sext + rAX sIz aso rexr rexx rexb @@ -7653,38 +8032,38 @@ aso oso rexw rexr rexx rexb 81 /reg=5 - Ev Iz - sext + Ev sIz aso rexr rexx rexb - 82 /reg=5 + 82 /reg=5 /m=!64 Eb Ib inv64 aso oso rexw rexr rexx rexb 83 /reg=5 - Ev Ib - sext + Ev sIb subpd - aso rexr rexx rexb - sse66 0f 5c - V W + aso rexr rexx rexb vexl + /sse=66 0f 5c + V H W + sse2 avx subps - aso rexr rexx rexb + aso rexr rexx rexb vexl 0f 5c - V W + V H W + sse avx @@ -7692,8 +8071,9 @@ subsd aso rexr rexx rexb - ssef2 0f 5c - V W + /sse=f2 0f 5c + V H W + sse2 avx @@ -7701,8 +8081,9 @@ subss aso rexr rexx rexb - ssef3 0f 5c - V W + /sse=f3 0f 5c + V H W + sse avx @@ -7723,15 +8104,22 @@ sysenter - 0f 34 - inv64 + 0f 34 /m=!64 + + + 0f 34 /m=64 + intel sysexit - 0f 35 + 0f 35 /m=!64 + + + 0f 35 /m=64 + intel @@ -7766,8 +8154,7 @@ oso rexw a9 - rAX Iz - sext + rAX sIz aso rexw rexr rexx rexb @@ -7777,14 +8164,12 @@ aso oso rexw rexr rexx rexb f7 /reg=0 - Ev Iz - sext + Ev sIz aso oso rexw rexr rexx rexb f7 /reg=1 Ev Iz - sext @@ -7792,8 +8177,9 @@ ucomisd aso rexr rexx rexb - sse66 0f 2e + /sse=66 0f 2e V W + sse2 avx @@ -7803,6 +8189,7 @@ aso rexr rexx rexb 0f 2e V W + sse avx @@ -7816,9 +8203,10 @@ unpckhpd - aso rexr rexx rexb - sse66 0f 15 - V W + aso rexr rexx rexb vexl + /sse=66 0f 15 + V H W + sse2 avx @@ -7827,7 +8215,8 @@ aso rexr rexx rexb 0f 15 - V W + V H W + sse avx @@ -7836,16 +8225,18 @@ aso rexr rexx rexb 0f 14 - V W + V H W + sse avx unpcklpd - aso rexr rexx rexb - sse66 0f 14 - V W + aso rexr rexx rexb vexl + /sse=66 0f 14 + V H W + sse2 avx @@ -7875,12 +8266,22 @@ + + rdrand + + oso rexr rexw rexx rexb + 0f c7 /mod=11 /reg=6 + R + + rdrand + + vmclear intel aso rexr rexx rexb - sse66 0f c7 /reg=6 + /sse=66 0f c7 /mod=!11 /reg=6 Mq @@ -7890,7 +8291,7 @@ intel aso rexr rexx rexb - ssef3 0f c7 /reg=6 + /sse=f3 0f c7 /mod=!11 /reg=6 Mq @@ -7900,7 +8301,7 @@ intel aso rexr rexx rexb - 0f c7 /reg=6 + 0f c7 /mod=!11 /reg=6 Mq @@ -7910,7 +8311,7 @@ intel aso rexr rexx rexb - 0f c7 /reg=7 + 0f c7 /mod=!11 /reg=7 Mq @@ -7944,20 +8345,8 @@ intel aso rexr rexx rexb - 0f 78 /m=16 - Ed Gd - def64 - - - aso rexr rexx rexb - 0f 78 /m=32 - Ed Gd - def64 - - - aso rexr rexx rexb - 0f 78 /m=64 - Eq Gq + 0f 78 + Ey Gy def64 @@ -7967,20 +8356,8 @@ intel aso rexr rexx rexb - 0f 79 /m=16 - Gd Ed - def64 - - - aso rexr rexx rexb - 0f 79 /m=32 - Gd Ed - def64 - - - aso rexr rexx rexb - 0f 79 /m=64 - Gq Eq + 0f 79 + Gy Ey def64 @@ -8067,49 +8444,56 @@ oso rexw rexb 90 - rAXr8 rAX + R0v rAX oso rexw rexb 91 - rCXr9 rAX + R1v rAX oso rexw rexb 92 - rDXr10 rAX + R2v rAX oso rexw rexb 93 - rBXr11 rAX + R3v rAX oso rexw rexb 94 - rSPr12 rAX + R4v rAX oso rexw rexb 95 - rBPr13 rAX + R5v rAX oso rexw rexb 96 - rSIr14 rAX + R6v rAX oso rexw rexb 97 - rDIr15 rAX + R7v rAX + + xgetbv + + 0f 01 /mod=11 /reg=2 /rm=0 + + + xlatb - rexw + rexw seg d7 @@ -8143,8 +8527,7 @@ oso rexw 35 - rAX Iz - sext + rAX sIz aso rexr rexx rexb @@ -8154,29 +8537,28 @@ aso oso rexw rexr rexx rexb 81 /reg=6 - Ev Iz - sext + Ev sIz aso rexr rexx rexb - 82 /reg=6 + 82 /reg=6 /m=!64 Eb Ib inv64 aso oso rexw rexr rexx rexb 83 /reg=6 - Ev Ib - sext + Ev sIb xorpd - aso rexr rexx rexb - sse66 0f 57 - V W + aso rexr rexx rexb vexl + /sse=66 0f 57 + V H W + sse2 avx @@ -8185,7 +8567,8 @@ aso rexr rexx rexb 0f 57 - V W + V H W + sse2 avx @@ -8224,6 +8607,31 @@ + + xrstor + + aso rexw rexr rexx rexb + 0f ae /reg=5 /mod=!11 + M + + + + + xsave + + aso rexw rexr rexx rexb + 0f ae /reg=4 /mod=!11 + M + + + + + xsetbv + + 0f 01 /mod=11 /reg=2 /rm=1 + + + xsha1 @@ -8246,7 +8654,25 @@ - db + pclmulqdq + + aso rexr rexx rexb + /sse=66 0f 3a 44 + V H W Ib + aesni avx + + + + + + + getsec + smx + + 0f 37 + - - addsubpd + haddpd - aso rexr rexx rexb - sse66 0f d0 - V W + aso rexr rexx rexb vexl + /sse=66 0f 7c + V H W + sse3 avx - addsubps + haddps - aso rexr rexx rexb - ssef2 0f d0 - V W + aso rexr rexx rexb vexl + /sse=f2 0f 7c + V H W + sse3 avx - haddpd + hsubpd - aso rexr rexx rexb - sse66 0f 7c - V W + aso rexr rexx rexb vexl + /sse=66 0f 7d + V H W + sse3 avx - haddps + hsubps - aso rexr rexx rexb - ssef2 0f 7c - V W + aso rexr rexx rexb vexl + /sse=f2 0f 7d + V H W + sse3 avx - hsubpd + insertps - aso rexr rexx rexb - sse66 0f 7d - V W + aso rexr rexw rexx rexb + /sse=66 0f 3a 21 + V H Md Ib + sse4.1 avx - hsubps + lddqu - aso rexr rexx rexb - ssef2 0f 7d - V W + aso rexr rexx rexb vexl + /sse=f2 0f f0 + V M + sse3 avx @@ -8466,41 +8915,46 @@ movddup aso rexr rexx rexb - ssef2 0f 12 /mod=11 + /sse=f2 0f 12 /mod=11 V W aso rexr rexx rexb - ssef2 0f 12 /mod=!11 + /sse=f2 0f 12 /mod=!11 V W + sse3 avx movshdup - aso rexr rexx rexb - ssef3 0f 16 /mod=11 + aso rexr rexx rexb vexl + /sse=f3 0f 16 /mod=11 V W + sse3 avx - aso rexr rexx rexb - ssef3 0f 16 /mod=!11 + aso rexr rexx rexb vexl + /sse=f3 0f 16 /mod=!11 V W + sse3 avx movsldup - aso rexr rexx rexb - ssef3 0f 12 /mod=11 + aso rexr rexx rexb vexl + /sse=f3 0f 12 /mod=11 V W + sse3 avx - aso rexr rexx rexb - ssef3 0f 12 /mod=!11 + aso rexr rexx rexb vexl + /sse=f3 0f 12 /mod=!11 V W + sse3 avx @@ -8514,11 +8968,13 @@ aso rexr rexx rexb 0f 38 1c P Q + ssse3 - aso rexr rexx rexb - sse66 0f 38 1c + aso rexr rexx rexb vexl + /sse=66 0f 38 1c V W + ssse3 avx @@ -8528,11 +8984,13 @@ aso rexr rexx rexb 0f 38 1d P Q + ssse3 - aso rexr rexx rexb - sse66 0f 38 1d + aso rexr rexx rexb vexl + /sse=66 0f 38 1d V W + ssse3 avx @@ -8542,16 +9000,18 @@ aso rexr rexx rexb 0f 38 1e P Q + ssse3 - aso rexr rexx rexb - sse66 0f 38 1e + aso rexr rexx rexb vexl + /sse=66 0f 38 1e V W + ssse3 avx - psignb + pshufb aso rexr rexx rexb 0f 38 00 @@ -8559,8 +9019,9 @@ aso rexr rexx rexb - sse66 0f 38 00 - V W + /sse=66 0f 38 00 + V H W + ssse3 avx @@ -8573,8 +9034,9 @@ aso rexr rexx rexb - sse66 0f 38 01 - V W + /sse=66 0f 38 01 + V H W + ssse3 avx @@ -8587,8 +9049,9 @@ aso rexr rexx rexb - sse66 0f 38 02 - V W + /sse=66 0f 38 02 + V H W + ssse3 avx @@ -8601,8 +9064,9 @@ aso rexr rexx rexb - sse66 0f 38 03 - V W + /sse=66 0f 38 03 + V H W + ssse3 avx @@ -8615,8 +9079,9 @@ aso rexr rexx rexb - sse66 0f 38 04 - V W + /sse=66 0f 38 04 + V H W + ssse3 avx @@ -8629,8 +9094,9 @@ aso rexr rexx rexb - sse66 0f 38 05 - V W + /sse=66 0f 38 05 + V H W + ssse3 avx @@ -8643,8 +9109,9 @@ aso rexr rexx rexb - sse66 0f 38 06 - V W + /sse=66 0f 38 06 + V H W + ssse3 avx @@ -8657,8 +9124,9 @@ aso rexr rexx rexb - sse66 0f 38 07 - V W + /sse=66 0f 38 07 + V H W + ssse3 avx @@ -8671,8 +9139,9 @@ aso rexr rexx rexb - sse66 0f 38 08 - V W + /sse=66 0f 38 08 + V H W + ssse3 avx @@ -8685,8 +9154,9 @@ aso rexr rexx rexb - sse66 0f 38 0a - V W + /sse=66 0f 38 0a + V H W + ssse3 avx @@ -8699,8 +9169,9 @@ aso rexr rexx rexb - sse66 0f 38 09 - V W + /sse=66 0f 38 09 + V H W + ssse3 avx @@ -8713,8 +9184,9 @@ aso rexr rexx rexb - sse66 0f 38 0b - V W + /sse=66 0f 38 0b + V H W + ssse3 avx @@ -8727,8 +9199,9 @@ aso rexr rexx rexb - sse66 0f 3a 0f - V W Ib + /sse=66 0f 3a 0f + V H W Ib + ssse3 avx @@ -8740,8 +9213,9 @@ pblendvb aso rexr rexx rexb - sse66 0f 38 10 + /sse=66 0f 38 10 V W + sse4.1 @@ -8749,8 +9223,9 @@ pmuldq aso rexr rexx rexb - sse66 0f 38 28 - V W + /sse=66 0f 38 28 + V H W + sse4.1 avx @@ -8758,8 +9233,9 @@ pminsb aso rexr rexx rexb - sse66 0f 38 38 - V W + /sse=66 0f 38 38 + V H W + sse4.1 avx @@ -8767,8 +9243,9 @@ pminsd aso rexr rexx rexb - sse66 0f 38 39 - V W + /sse=66 0f 38 39 + V H W + sse4.1 avx @@ -8776,8 +9253,9 @@ pminuw aso rexr rexx rexb - sse66 0f 38 3a - V W + /sse=66 0f 38 3a + V H W + sse4.1 avx @@ -8785,8 +9263,9 @@ pminud aso rexr rexx rexb - sse66 0f 38 3b - V W + /sse=66 0f 38 3b + V H W + sse4.1 avx @@ -8794,8 +9273,9 @@ pmaxsb aso rexr rexx rexb - sse66 0f 38 3c - V W + /sse=66 0f 38 3c + V H W + sse4.1 avx @@ -8803,8 +9283,9 @@ pmaxsd aso rexr rexx rexb - sse66 0f 38 3d - V W + /sse=66 0f 38 3d + V H W + sse4.1 avx @@ -8812,8 +9293,19 @@ pmaxud aso rexr rexx rexb - sse66 0f 38 3f - V W + /sse=66 0f 38 3f + V H W + sse4.1 avx + + + + + pmaxuw + + aso rexr rexx rexb + /sse=66 0f 38 3e + V H W + sse4.1 avx @@ -8821,8 +9313,9 @@ pmulld aso rexr rexx rexb - sse66 0f 38 40 - V W + /sse=66 0f 38 40 + V H W + sse4.1 avx @@ -8830,26 +9323,29 @@ phminposuw aso rexr rexx rexb - sse66 0f 38 41 + /sse=66 0f 38 41 V W + sse4.1 avx roundps - aso rexr rexx rexb - sse66 0f 3a 08 + aso rexr rexx rexb vexl + /sse=66 0f 3a 08 V W Ib + sse avx roundpd - aso rexr rexx rexb - sse66 0f 3a 09 + aso rexr rexx rexb vexl + /sse=66 0f 3a 09 V W Ib + sse4.1 avx @@ -8857,8 +9353,9 @@ roundss aso rexr rexx rexb - sse66 0f 3a 0a - V W Ib + /sse=66 0f 3a 0a + V H W Ib + sse4.1 avx @@ -8866,89 +9363,448 @@ roundsd aso rexr rexx rexb - sse66 0f 3a 0b - V W Ib + /sse=66 0f 3a 0b + V H W Ib + sse4.1 avx blendpd - aso rexr rexx rexb - sse66 0f 3a 0d - V W Ib + aso rexr rexx rexb vexl + /sse=66 0f 3a 0d + V H W Ib + sse4.1 avx - pblendw + blendps aso rexr rexx rexb - sse66 0f 3a 0e - V W Ib + /sse=66 0f 3a 0c + V H W Ib + sse4.1 avx - blendps + blendvpd aso rexr rexx rexb - sse66 0f 3a 0c - V W Ib + /sse=66 0f 38 15 + V W + sse4.1 - blendvpd + blendvps aso rexr rexx rexb - sse66 0f 38 15 + /sse=66 0f 38 14 V W + sse4.1 - blendvps + bound + + aso oso + 62 /m=!64 + Gv M + + + + + bsf + + aso oso rexw rexr rexx rexb + 0f bc + Gv Ev + + + + + bsr + + aso oso rexw rexr rexx rexb + 0f bd + Gv Ev + + + + + bswap + + oso rexw rexb + 0f c8 + R0y + + + oso rexw rexb + 0f c9 + R1y + + + oso rexw rexb + 0f ca + R2y + + + oso rexw rexb + 0f cb + R3y + + + oso rexw rexb + 0f cc + R4y + + + oso rexw rexb + 0f cd + R5y + + + oso rexw rexb + 0f ce + R6y + + + oso rexw rexb + 0f cf + R7y + + + + + bt + + aso oso rexw rexr rexx rexb + 0f ba /reg=4 + Ev Ib + + + aso oso rexw rexr rexx rexb + 0f a3 + Ev Gv + + + + + btc + + aso oso rexw rexr rexx rexb + 0f bb + Ev Gv + + + aso oso rexw rexr rexx rexb + 0f ba /reg=7 + Ev Ib + + + + + btr + + aso oso rexw rexr rexx rexb + 0f b3 + Ev Gv + + + aso oso rexw rexr rexx rexb + 0f ba /reg=6 + Ev Ib + + + + + bts + + aso oso rexw rexr rexx rexb + 0f ab + Ev Gv + + + aso oso rexw rexr rexx rexb + 0f ba /reg=5 + Ev Ib + + + + + pblendw aso rexr rexx rexb - sse66 0f 38 14 + /sse=66 0f 3a 0e + V H W Ib + sse4.1 avx + + + + + mpsadbw + + aso rexr rexx rexb vexl + /sse=66 0f 3a 42 + V H W Ib + sse4.1 avx + + + + + movntdqa + + aso rexr rexw rexx rexb vexl + /sse=66 0f 38 2a + V M + sse4.1 avx + + + + + packusdw + + aso rexr rexw rexx rexb vexl + /sse=66 0f 38 2b + V H W + sse2 avx + + + + + pmovsxbw + + aso rexr rexw rexx rexb + /sse=66 0f 38 20 + V MqU + sse4.1 avx + + + + + pmovsxbd + + aso rexr rexw rexx rexb + /sse=66 0f 38 21 + V MdU + sse4.1 avx + + + + + pmovsxbq + + aso rexr rexw rexx rexb + /sse=66 0f 38 22 + V MwU + sse4.1 avx + + + + + pmovsxwd + + aso rexr rexw rexx rexb + /sse=66 0f 38 23 + V MqU + sse4.1 avx + + + + + pmovsxwq + + aso rexr rexw rexx rexb + /sse=66 0f 38 24 + V MdU + sse4.1 avx + + + + + pmovsxdq + + aso rexr rexw rexx rexb + /sse=66 0f 38 25 + V MqU + sse4.1 + + + + + pmovzxbw + + aso rexr rexw rexx rexb + /sse=66 0f 38 30 + V MqU + sse4.1 avx + + + + + pmovzxbd + + aso rexr rexw rexx rexb + /sse=66 0f 38 31 + V MdU + sse4.1 avx + + + + + pmovzxbq + + aso rexr rexw rexx rexb + /sse=66 0f 38 32 + V MwU + sse4.1 avx + + + + + pmovzxwd + + aso rexr rexw rexx rexb + /sse=66 0f 38 33 + V MqU + sse4.1 avx + + + + + pmovzxwq + + aso rexr rexw rexx rexb + /sse=66 0f 38 34 + V MdU + sse4.1 avx + + + + + pmovzxdq + + aso rexr rexw rexx rexb + /sse=66 0f 38 35 + V MqU + sse4.1 avx + + + + + pcmpeqq + + aso rexr rexw rexx rexb + /sse=66 0f 38 29 + V H W + sse4.1 avx + + + + + popcnt + + aso oso rexr rexw rexx rexb + /sse=f3 0f b8 + Gv Ev + + sse4.2 + + + + ptest + + aso rexr rexw rexx rexb vexl + /sse=66 0f 38 17 V W + sse4.1 avx - dpps + pcmpestri - aso rexr rexx rexb - sse66 0f 3a 40 + aso rexr rexw rexx rexb + /sse=66 0f 3a 61 V W Ib + sse4.2 avx - dppd + pcmpestrm - aso rexr rexx rexb - sse66 0f 3a 41 + aso rexr rexw rexx rexb + /sse=66 0f 3a 60 V W Ib + sse4.2 avx - mpsadbw + pcmpgtq - aso rexr rexx rexb - sse66 0f 3a 42 + aso rexr rexw rexx rexb + /sse=66 0f 38 37 + V H W + sse4.2 avx + + + + + pcmpistri + + aso rexr rexw rexx rexb + /sse=66 0f 3a 63 V W Ib + sse4.2 avx - extractps + pcmpistrm - aso rexr rexw rexb - sse66 0f 3a 17 - MdRy V Ib + aso rexr rexw rexx rexb + /sse=66 0f 3a 62 + V W Ib + sse4.2 avx + + + + + movbe + + aso oso rexr rexw rexx rexb + 0f 38 f0 + Gv Mv + sse3 atom + + + aso oso rexr rexw rexx rexb + 0f 38 f1 + Mv Gv + sse3 atom + + + + + crc32 + + aso oso rexr rexw rexx rexb + /sse=f2 0f 38 f0 + Gy Eb + sse4.2 + + + aso oso rexr rexw rexx rexb + /sse=f2 0f 38 f1 + Gy Ev + sse4.2 @@ -8956,4 +9812,288 @@ invalid + + vbroadcastss + + aso rexr rexx rexb vexl + /vex=66_0f38 18 /vexw=0 + V Md + avx + + + + + vbroadcastsd + + aso rexr rexx rexb vexl + /vex=66_0f38 19 /vexw=0 /vexl=1 + Vqq Mq + avx + + + + + vextractf128 + + aso rexr rexx rexb vexl + /vex=66_0f3a 19 /vexw=0 /vexl=1 + Wdq Vqq Ib + avx + + + + + vinsertf128 + + aso rexr rexx rexb vexl + /vex=66_0f3a 18 /vexw=0 /vexl=1 + Vqq Hqq Wdq Ib + avx + + + + + vmaskmovps + + aso rexr rexx rexb vexl + /vex=66_0f38 2c /vexw=0 + V H M + avx + + + aso rexr rexx rexb vexl + /vex=66_0f38 2e /vexw=0 + M H V + avx + + + + + vmaskmovpd + + aso rexr rexx rexb vexl + /vex=66_0f38 2d /vexw=0 + V H M + avx + + + aso rexr rexx rexb vexl + /vex=66_0f38 2f /vexw=0 + M H V + avx + + + + + vpermilpd + + aso rexr rexx rexb vexl + /vex=66_0f38 0d /vexw=0 + Vx Hx Wx + avx + + + aso rexr rexx rexb vexl + /vex=66_0f3a 05 /vexw=0 + V W Ib + avx + + + + + vpermilps + + aso rexr rexx rexb vexl + /vex=66_0f38 0c /vexw=0 + Vx Hx Wx + avx + + + aso rexr rexx rexb vexl + /vex=66_0f3a 04 /vexw=0 + Vx Wx Ib + avx + + + + + vperm2f128 + + aso rexr rexx rexb vexl + /vex=66_0f3a 06 /vexw=0 /vexl=1 + Vqq Hqq Wqq Ib + avx + + + + + vtestps + + aso rexr rexx rexb vexl + /vex=66_0f38 0e /vexw=0 + Vx Wx + avx + + + + + vtestpd + + aso rexr rexx rexb vexl + /vex=66_0f38 0f /vexw=0 + Vx Wx + avx + + + + + vzeroupper + + /vex=0f 77 /vexl=0 + avx + + + + + vzeroall + + /vex=0f 77 /vexl=1 + avx + + + + + vblendvpd + + aso rexr rexx rexb vexl + /vex=66_0f3a 4b /vexw=0 + Vx Hx Wx Lx + avx + + + + + vblendvps + + aso rexr rexx rexb vexl + /vex=66_0f3a 4a /vexw=0 + Vx Hx Wx Lx + avx + + + + + vmovsd + + aso rexr rexx rexb + /vex=f2_0f 10 /mod=11 + V H U + avx + + + aso rexr rexx rexb + /vex=f2_0f 10 /mod=!11 + V Mq + avx + + + aso rexr rexx rexb + /vex=f2_0f 11 /mod=11 + U H V + avx + + + aso rexr rexx rexb + /vex=f2_0f 11 /mod=!11 + Mq V + avx + + + + + vmovss + + aso rexr rexx rexb + /vex=f3_0f 10 /mod=11 + V H U + avx + + + aso rexr rexx rexb + /vex=f3_0f 10 /mod=!11 + V Md + avx + + + aso rexr rexx rexb + /vex=f3_0f 11 /mod=11 + U H V + avx + + + aso rexr rexx rexb + /vex=f3_0f 11 /mod=!11 + Md V + avx + + + + + vpblendvb + + aso rexr rexx rexb + /vex=66_0f3a 4c /vexw=0 + V H W L + avx + + + + + vpsllw + + aso rexr rexx rexb + /vex=66_0f f1 /vexl=0 + V H W + avx + + + aso rexr rexx rexb + /vex=66_0f 71 /reg=6 /vexl=0 + H V W + avx + + + + + vpslld + + aso rexr rexx rexb + /vex=66_0f f2 /vexl=0 + V H W + avx + + + aso rexr rexx rexb + /vex=66_0f 72 /reg=6 /vexl=0 + H V W + avx + + + + + vpsllq + + aso rexr rexx rexb + /vex=66_0f f3 /vexl=0 + V H W + avx + + + aso rexr rexx rexb + /vex=66_0f 73 /reg=6 /vexl=0 + H V W + avx + + + diff --git a/Source/JavaScriptCore/disassembler/udis86/ud_itab.py b/Source/JavaScriptCore/disassembler/udis86/ud_itab.py new file mode 100644 index 000000000..ef011d2ec --- /dev/null +++ b/Source/JavaScriptCore/disassembler/udis86/ud_itab.py @@ -0,0 +1,379 @@ +# udis86 - scripts/ud_itab.py +# +# Copyright (c) 2009, 2013 Vivek Thampi +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above copyright notice, +# this list of conditions and the following disclaimer in the documentation +# and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +import os +import sys +from ud_opcode import UdOpcodeTable, UdOpcodeTables, UdInsnDef + +class UdItabGenerator: + + OperandDict = { + "Av" : [ "OP_A" , "SZ_V" ], + "E" : [ "OP_E" , "SZ_NA" ], + "Eb" : [ "OP_E" , "SZ_B" ], + "Ew" : [ "OP_E" , "SZ_W" ], + "Ev" : [ "OP_E" , "SZ_V" ], + "Ed" : [ "OP_E" , "SZ_D" ], + "Ey" : [ "OP_E" , "SZ_Y" ], + "Eq" : [ "OP_E" , "SZ_Q" ], + "Ez" : [ "OP_E" , "SZ_Z" ], + "Fv" : [ "OP_F" , "SZ_V" ], + "G" : [ "OP_G" , "SZ_NA" ], + "Gb" : [ "OP_G" , "SZ_B" ], + "Gw" : [ "OP_G" , "SZ_W" ], + "Gv" : [ "OP_G" , "SZ_V" ], + "Gy" : [ "OP_G" , "SZ_Y" ], + "Gd" : [ "OP_G" , "SZ_D" ], + "Gq" : [ "OP_G" , "SZ_Q" ], + "Gz" : [ "OP_G" , "SZ_Z" ], + "M" : [ "OP_M" , "SZ_NA" ], + "Mb" : [ "OP_M" , "SZ_B" ], + "Mw" : [ "OP_M" , "SZ_W" ], + "Ms" : [ "OP_M" , "SZ_W" ], + "Md" : [ "OP_M" , "SZ_D" ], + "Mq" : [ "OP_M" , "SZ_Q" ], + "Mdq" : [ "OP_M" , "SZ_DQ" ], + "Mv" : [ "OP_M" , "SZ_V" ], + "Mt" : [ "OP_M" , "SZ_T" ], + "Mo" : [ "OP_M" , "SZ_O" ], + "MbRd" : [ "OP_MR" , "SZ_BD" ], + "MbRv" : [ "OP_MR" , "SZ_BV" ], + "MwRv" : [ "OP_MR" , "SZ_WV" ], + "MwRd" : [ "OP_MR" , "SZ_WD" ], + "MwRy" : [ "OP_MR" , "SZ_WY" ], + "MdRy" : [ "OP_MR" , "SZ_DY" ], + "I1" : [ "OP_I1" , "SZ_NA" ], + "I3" : [ "OP_I3" , "SZ_NA" ], + "Ib" : [ "OP_I" , "SZ_B" ], + "Iw" : [ "OP_I" , "SZ_W" ], + "Iv" : [ "OP_I" , "SZ_V" ], + "Iz" : [ "OP_I" , "SZ_Z" ], + "sIb" : [ "OP_sI" , "SZ_B" ], + "sIz" : [ "OP_sI" , "SZ_Z" ], + "sIv" : [ "OP_sI" , "SZ_V" ], + "Jv" : [ "OP_J" , "SZ_V" ], + "Jz" : [ "OP_J" , "SZ_Z" ], + "Jb" : [ "OP_J" , "SZ_B" ], + "R" : [ "OP_R" , "SZ_RDQ" ], + "C" : [ "OP_C" , "SZ_NA" ], + "D" : [ "OP_D" , "SZ_NA" ], + "S" : [ "OP_S" , "SZ_W" ], + "Ob" : [ "OP_O" , "SZ_B" ], + "Ow" : [ "OP_O" , "SZ_W" ], + "Ov" : [ "OP_O" , "SZ_V" ], + "U" : [ "OP_U" , "SZ_O" ], + "Ux" : [ "OP_U" , "SZ_X" ], + "V" : [ "OP_V" , "SZ_DQ" ], + "Vdq" : [ "OP_V" , "SZ_DQ" ], + "Vqq" : [ "OP_V" , "SZ_QQ" ], + "Vsd" : [ "OP_V" , "SZ_Q" ], + "Vx" : [ "OP_V" , "SZ_X" ], + "H" : [ "OP_H" , "SZ_X" ], + "Hx" : [ "OP_H" , "SZ_X" ], + "Hqq" : [ "OP_H" , "SZ_QQ" ], + "W" : [ "OP_W" , "SZ_DQ" ], + "Wdq" : [ "OP_W" , "SZ_DQ" ], + "Wqq" : [ "OP_W" , "SZ_QQ" ], + "Wsd" : [ "OP_W" , "SZ_Q" ], + "Wx" : [ "OP_W" , "SZ_X" ], + "L" : [ "OP_L" , "SZ_O" ], + "Lx" : [ "OP_L" , "SZ_X" ], + "MwU" : [ "OP_MU" , "SZ_WO" ], + "MdU" : [ "OP_MU" , "SZ_DO" ], + "MqU" : [ "OP_MU" , "SZ_QO" ], + "N" : [ "OP_N" , "SZ_Q" ], + "P" : [ "OP_P" , "SZ_Q" ], + "Q" : [ "OP_Q" , "SZ_Q" ], + "AL" : [ "OP_AL" , "SZ_B" ], + "AX" : [ "OP_AX" , "SZ_W" ], + "eAX" : [ "OP_eAX" , "SZ_Z" ], + "rAX" : [ "OP_rAX" , "SZ_V" ], + "CL" : [ "OP_CL" , "SZ_B" ], + "CX" : [ "OP_CX" , "SZ_W" ], + "eCX" : [ "OP_eCX" , "SZ_Z" ], + "rCX" : [ "OP_rCX" , "SZ_V" ], + "DL" : [ "OP_DL" , "SZ_B" ], + "DX" : [ "OP_DX" , "SZ_W" ], + "eDX" : [ "OP_eDX" , "SZ_Z" ], + "rDX" : [ "OP_rDX" , "SZ_V" ], + "R0b" : [ "OP_R0" , "SZ_B" ], + "R1b" : [ "OP_R1" , "SZ_B" ], + "R2b" : [ "OP_R2" , "SZ_B" ], + "R3b" : [ "OP_R3" , "SZ_B" ], + "R4b" : [ "OP_R4" , "SZ_B" ], + "R5b" : [ "OP_R5" , "SZ_B" ], + "R6b" : [ "OP_R6" , "SZ_B" ], + "R7b" : [ "OP_R7" , "SZ_B" ], + "R0w" : [ "OP_R0" , "SZ_W" ], + "R1w" : [ "OP_R1" , "SZ_W" ], + "R2w" : [ "OP_R2" , "SZ_W" ], + "R3w" : [ "OP_R3" , "SZ_W" ], + "R4w" : [ "OP_R4" , "SZ_W" ], + "R5w" : [ "OP_R5" , "SZ_W" ], + "R6w" : [ "OP_R6" , "SZ_W" ], + "R7w" : [ "OP_R7" , "SZ_W" ], + "R0v" : [ "OP_R0" , "SZ_V" ], + "R1v" : [ "OP_R1" , "SZ_V" ], + "R2v" : [ "OP_R2" , "SZ_V" ], + "R3v" : [ "OP_R3" , "SZ_V" ], + "R4v" : [ "OP_R4" , "SZ_V" ], + "R5v" : [ "OP_R5" , "SZ_V" ], + "R6v" : [ "OP_R6" , "SZ_V" ], + "R7v" : [ "OP_R7" , "SZ_V" ], + "R0z" : [ "OP_R0" , "SZ_Z" ], + "R1z" : [ "OP_R1" , "SZ_Z" ], + "R2z" : [ "OP_R2" , "SZ_Z" ], + "R3z" : [ "OP_R3" , "SZ_Z" ], + "R4z" : [ "OP_R4" , "SZ_Z" ], + "R5z" : [ "OP_R5" , "SZ_Z" ], + "R6z" : [ "OP_R6" , "SZ_Z" ], + "R7z" : [ "OP_R7" , "SZ_Z" ], + "R0y" : [ "OP_R0" , "SZ_Y" ], + "R1y" : [ "OP_R1" , "SZ_Y" ], + "R2y" : [ "OP_R2" , "SZ_Y" ], + "R3y" : [ "OP_R3" , "SZ_Y" ], + "R4y" : [ "OP_R4" , "SZ_Y" ], + "R5y" : [ "OP_R5" , "SZ_Y" ], + "R6y" : [ "OP_R6" , "SZ_Y" ], + "R7y" : [ "OP_R7" , "SZ_Y" ], + "ES" : [ "OP_ES" , "SZ_NA" ], + "CS" : [ "OP_CS" , "SZ_NA" ], + "DS" : [ "OP_DS" , "SZ_NA" ], + "SS" : [ "OP_SS" , "SZ_NA" ], + "GS" : [ "OP_GS" , "SZ_NA" ], + "FS" : [ "OP_FS" , "SZ_NA" ], + "ST0" : [ "OP_ST0" , "SZ_NA" ], + "ST1" : [ "OP_ST1" , "SZ_NA" ], + "ST2" : [ "OP_ST2" , "SZ_NA" ], + "ST3" : [ "OP_ST3" , "SZ_NA" ], + "ST4" : [ "OP_ST4" , "SZ_NA" ], + "ST5" : [ "OP_ST5" , "SZ_NA" ], + "ST6" : [ "OP_ST6" , "SZ_NA" ], + "ST7" : [ "OP_ST7" , "SZ_NA" ], + "NONE" : [ "OP_NONE" , "SZ_NA" ], + } + + # + # opcode prefix dictionary + # + PrefixDict = { + "rep" : "P_str", + "repz" : "P_strz", + "aso" : "P_aso", + "oso" : "P_oso", + "rexw" : "P_rexw", + "rexb" : "P_rexb", + "rexx" : "P_rexx", + "rexr" : "P_rexr", + "vexl" : "P_vexl", + "vexw" : "P_vexw", + "seg" : "P_seg", + "inv64" : "P_inv64", + "def64" : "P_def64", + "cast" : "P_cast", + } + + MnemonicAliases = ( "invalid", "3dnow", "none", "db", "pause" ) + + def __init__(self, tables): + self.tables = tables + self._insnIndexMap, i = {}, 0 + for insn in tables.getInsnList(): + self._insnIndexMap[insn], i = i, i + 1 + + self._tableIndexMap, i = {}, 0 + for table in tables.getTableList(): + self._tableIndexMap[table], i = i, i + 1 + + def getInsnIndex(self, insn): + assert isinstance(insn, UdInsnDef) + return self._insnIndexMap[insn] + + def getTableIndex(self, table): + assert isinstance(table, UdOpcodeTable) + return self._tableIndexMap[table] + + def getTableName(self, table): + return "ud_itab__%d" % self.getTableIndex(table) + + def genOpcodeTable(self, table, isGlobal=False): + """Emit Opcode Table in C. + """ + self.ItabC.write( "\n" ); + if not isGlobal: + self.ItabC.write('static ') + self.ItabC.write( "const uint16_t %s[] = {\n" % self.getTableName(table)) + for i in range(table.size()): + if i > 0 and i % 4 == 0: + self.ItabC.write( "\n" ) + if i % 4 == 0: + self.ItabC.write( " /* %2x */" % i) + e = table.entryAt(i) + if e is None: + self.ItabC.write("%12s," % "INVALID") + elif isinstance(e, UdOpcodeTable): + self.ItabC.write("%12s," % ("GROUP(%d)" % self.getTableIndex(e))) + elif isinstance(e, UdInsnDef): + self.ItabC.write("%12s," % self.getInsnIndex(e)) + self.ItabC.write( "\n" ) + self.ItabC.write( "};\n" ) + + + def genOpcodeTables(self): + tables = self.tables.getTableList() + for table in tables: + self.genOpcodeTable(table, table is self.tables.root) + + + def genOpcodeTablesLookupIndex(self): + self.ItabC.write( "\n\n" ); + self.ItabC.write( "struct ud_lookup_table_list_entry ud_lookup_table_list[] = {\n" ) + for table in self.tables.getTableList(): + f0 = self.getTableName(table) + "," + f1 = table.label() + "," + f2 = "\"%s\"" % table.meta() + self.ItabC.write(" /* %03d */ { %s %s %s },\n" % + (self.getTableIndex(table), f0, f1, f2)) + self.ItabC.write( "};" ) + + + def genInsnTable( self ): + self.ItabC.write( "struct ud_itab_entry ud_itab[] = {\n" ); + for insn in self.tables.getInsnList(): + opr_c = [ "O_NONE", "O_NONE", "O_NONE", "O_NONE" ] + pfx_c = [] + opr = insn.operands + for i in range(len(opr)): + if not (opr[i] in self.OperandDict.keys()): + print("error: invalid operand declaration: %s\n" % opr[i]) + opr_c[i] = "O_" + opr[i] + opr = "%s %s %s %s" % (opr_c[0] + ",", opr_c[1] + ",", + opr_c[2] + ",", opr_c[3]) + + for p in insn.prefixes: + if not ( p in self.PrefixDict.keys() ): + print("error: invalid prefix specification: %s \n" % pfx) + pfx_c.append( self.PrefixDict[p] ) + if len(insn.prefixes) == 0: + pfx_c.append( "P_none" ) + pfx = "|".join( pfx_c ) + + self.ItabC.write( " /* %04d */ { UD_I%s %s, %s },\n" \ + % ( self.getInsnIndex(insn), insn.mnemonic + ',', opr, pfx ) ) + self.ItabC.write( "};\n" ) + + + def getMnemonicsList(self): + mnemonics = self.tables.getMnemonicsList() + mnemonics.extend(self.MnemonicAliases) + return mnemonics + + def genMnemonicsList(self): + mnemonics = self.getMnemonicsList() + self.ItabC.write( "\n\n" ); + self.ItabC.write( "const char* ud_mnemonics_str[] = {\n " ) + self.ItabC.write( ",\n ".join( [ "\"%s\"" % m for m in mnemonics ] ) ) + self.ItabC.write( "\n};\n" ) + + + def genItabH( self, filePath ): + self.ItabH = open( filePath, "w" ) + + # Generate Table Type Enumeration + self.ItabH.write( "#ifndef UD_ITAB_H\n" ) + self.ItabH.write( "#define UD_ITAB_H\n\n" ) + + self.ItabH.write("/* itab.h -- generated by udis86:scripts/ud_itab.py, do no edit */\n\n") + + # table type enumeration + self.ItabH.write( "/* ud_table_type -- lookup table types (see decode.c) */\n" ) + self.ItabH.write( "enum ud_table_type {\n " ) + enum = UdOpcodeTable.getLabels() + self.ItabH.write( ",\n ".join( enum ) ) + self.ItabH.write( "\n};\n\n" ); + + # mnemonic enumeration + self.ItabH.write( "/* ud_mnemonic -- mnemonic constants */\n" ) + enum = "enum ud_mnemonic_code {\n " + enum += ",\n ".join( [ "UD_I%s" % m for m in self.getMnemonicsList() ] ) + enum += ",\n UD_MAX_MNEMONIC_CODE" + enum += "\n};\n" + self.ItabH.write( enum ) + self.ItabH.write( "\n" ) + + self.ItabH.write( "extern const char * ud_mnemonics_str[];\n" ) + + self.ItabH.write( "\n#endif /* UD_ITAB_H */\n" ) + + self.ItabH.close() + + + def genItabC(self, filePath): + self.ItabC = open(filePath, "w") + self.ItabC.write("/* itab.c -- generated by udis86:scripts/ud_itab.py, do no edit") + self.ItabC.write(" */\n"); + self.ItabC.write("#include \"udis86_decode.h\"\n\n"); + + self.ItabC.write("#define GROUP(n) (0x8000 | (n))\n") + self.ItabC.write("#define INVALID %d\n\n" % self.getInsnIndex(self.tables.invalidInsn)) + + self.genOpcodeTables() + self.genOpcodeTablesLookupIndex() + + # + # Macros defining short-names for operands + # + self.ItabC.write("\n\n/* itab entry operand definitions (for readability) */\n"); + operands = self.OperandDict.keys() + operands = sorted(operands) + for o in operands: + self.ItabC.write("#define O_%-7s { %-12s %-8s }\n" % + (o, self.OperandDict[o][0] + ",", self.OperandDict[o][1])); + self.ItabC.write("\n"); + + self.genInsnTable() + self.genMnemonicsList() + + self.ItabC.close() + + def genItab( self, location ): + self.genItabC(os.path.join(location, "udis86_itab.c")) + self.genItabH(os.path.join(location, "udis86_itab.h")) + +def usage(): + print("usage: ud_itab.py ") + +def main(): + + if len(sys.argv) != 3: + usage() + sys.exit(1) + + tables = UdOpcodeTables(xml=sys.argv[1]) + itab = UdItabGenerator(tables) + itab.genItab(sys.argv[2]) + +if __name__ == '__main__': + main() diff --git a/Source/JavaScriptCore/disassembler/udis86/ud_opcode.py b/Source/JavaScriptCore/disassembler/udis86/ud_opcode.py index f82738062..fe1833dc7 100644 --- a/Source/JavaScriptCore/disassembler/udis86/ud_opcode.py +++ b/Source/JavaScriptCore/disassembler/udis86/ud_opcode.py @@ -1,6 +1,6 @@ # udis86 - scripts/ud_opcode.py # -# Copyright (c) 2009 Vivek Thampi +# Copyright (c) 2009, 2013 Vivek Thampi # All rights reserved. # # Redistribution and use in source and binary forms, with or without modification, @@ -23,213 +23,600 @@ # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS # SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -class UdOpcodeTables: - - TableInfo = { - 'opctbl' : { 'name' : 'UD_TAB__OPC_TABLE', 'size' : 256 }, - '/sse' : { 'name' : 'UD_TAB__OPC_SSE', 'size' : 4 }, - '/reg' : { 'name' : 'UD_TAB__OPC_REG', 'size' : 8 }, - '/rm' : { 'name' : 'UD_TAB__OPC_RM', 'size' : 8 }, - '/mod' : { 'name' : 'UD_TAB__OPC_MOD', 'size' : 2 }, - '/m' : { 'name' : 'UD_TAB__OPC_MODE', 'size' : 3 }, - '/x87' : { 'name' : 'UD_TAB__OPC_X87', 'size' : 64 }, - '/a' : { 'name' : 'UD_TAB__OPC_ASIZE', 'size' : 3 }, - '/o' : { 'name' : 'UD_TAB__OPC_OSIZE', 'size' : 3 }, - '/3dnow' : { 'name' : 'UD_TAB__OPC_3DNOW', 'size' : 256 }, - 'vendor' : { 'name' : 'UD_TAB__OPC_VENDOR', 'size' : 3 }, - } +import os + +# Some compatibility stuff for supporting python 2.x as well as python 3.x +def itemslist(dict): + try: + return dict.iteritems() # python 2.x + except AttributeError: + return list(dict.items()) # python 3.x + +class UdInsnDef: + """An x86 instruction definition + """ + def __init__(self, **insnDef): + self.mnemonic = insnDef['mnemonic'] + self.prefixes = insnDef['prefixes'] + self.opcodes = insnDef['opcodes'] + self.operands = insnDef['operands'] + self._cpuid = insnDef['cpuid'] + self._opcexts = {} + + for opc in self.opcodes: + if opc.startswith('/'): + e, v = opc.split('=') + self._opcexts[e] = v + + def lookupPrefix(self, pfx): + """Lookup prefix (if any, None otherwise), by name""" + return True if pfx in self.prefixes else None + + + @property + def vendor(self): + return self._opcexts.get('/vendor', None) + + @property + def mode(self): + return self._opcexts.get('/m', None) + + @property + def osize(self): + return self._opcexts.get('/o', None) + + def isDef64(self): + return 'def64' in self.prefixes + + def __str__(self): + return self.mnemonic + " " + ', '.join(self.operands) + \ + " " + ' '.join(self.opcodes) - OpcodeTable0 = { - 'type' : 'opctbl', - 'entries' : {}, - 'meta' : 'table0' - } - OpcExtIndex = { - - # ssef2, ssef3, sse66 - 'sse': { - 'none' : '00', - 'f2' : '01', - 'f3' : '02', - '66' : '03' - }, - - # /mod= - 'mod': { - '!11' : '00', - '11' : '01' - }, - - # /m=, /o=, /a= - 'mode': { - '16' : '00', - '32' : '01', - '64' : '02' - }, - - 'vendor' : { - 'amd' : '00', - 'intel' : '01', - 'any' : '02' +class UdOpcodeTable: + """A single table of instruction definitions, indexed by + a decode field. + """ + + class CollisionError(Exception): + pass + + class IndexError(Exception): + """Invalid Index Error""" + pass + + @classmethod + def vendor2idx(cls, v): + return (0 if v == 'amd' + else (1 if v == 'intel' + else 2)) + + @classmethod + def vex2idx(cls, v): + if v.startswith("none_"): + v = v[5:] + vexOpcExtMap = { + 'none' : 0x0, + '0f' : 0x1, + '0f38' : 0x2, + '0f3a' : 0x3, + '66' : 0x4, + '66_0f' : 0x5, + '66_0f38' : 0x6, + '66_0f3a' : 0x7, + 'f3' : 0x8, + 'f3_0f' : 0x9, + 'f3_0f38' : 0xa, + 'f3_0f3a' : 0xb, + 'f2' : 0xc, + 'f2_0f' : 0xd, + 'f2_0f38' : 0xe, + 'f2_0f3a' : 0xf, } + return vexOpcExtMap[v] + + + # A mapping of opcode extensions to their representational + # values used in the opcode map. + OpcExtMap = { + '/rm' : lambda v: int(v, 16), + '/x87' : lambda v: int(v, 16), + '/3dnow' : lambda v: int(v, 16), + '/reg' : lambda v: int(v, 16), + # modrm.mod + # (!11, 11) => (00b, 01b) + '/mod' : lambda v: 0 if v == '!11' else 1, + # Mode extensions: + # (16, 32, 64) => (00, 01, 02) + '/o' : lambda v: (int(v) / 32), + '/a' : lambda v: (int(v) / 32), + # Disassembly mode + # (!64, 64) => (00b, 01b) + '/m' : lambda v: 1 if v == '64' else 0, + # SSE + # none => 0 + # f2 => 1 + # f3 => 2 + # 66 => 3 + '/sse' : lambda v: (0 if v == 'none' + else (((int(v, 16) & 0xf) + 1) / 2)), + # AVX + '/vex' : lambda v: UdOpcodeTable.vex2idx(v), + '/vexw' : lambda v: 0 if v == '0' else 1, + '/vexl' : lambda v: 0 if v == '0' else 1, + # Vendor + '/vendor': lambda v: UdOpcodeTable.vendor2idx(v) } - InsnTable = [] - MnemonicsTable = [] - ThreeDNowTable = {} + _TableInfo = { + 'opctbl' : { 'label' : 'UD_TAB__OPC_TABLE', 'size' : 256 }, + '/sse' : { 'label' : 'UD_TAB__OPC_SSE', 'size' : 4 }, + '/reg' : { 'label' : 'UD_TAB__OPC_REG', 'size' : 8 }, + '/rm' : { 'label' : 'UD_TAB__OPC_RM', 'size' : 8 }, + '/mod' : { 'label' : 'UD_TAB__OPC_MOD', 'size' : 2 }, + '/m' : { 'label' : 'UD_TAB__OPC_MODE', 'size' : 2 }, + '/x87' : { 'label' : 'UD_TAB__OPC_X87', 'size' : 64 }, + '/a' : { 'label' : 'UD_TAB__OPC_ASIZE', 'size' : 3 }, + '/o' : { 'label' : 'UD_TAB__OPC_OSIZE', 'size' : 3 }, + '/3dnow' : { 'label' : 'UD_TAB__OPC_3DNOW', 'size' : 256 }, + '/vendor' : { 'label' : 'UD_TAB__OPC_VENDOR', 'size' : 3 }, + '/vex' : { 'label' : 'UD_TAB__OPC_VEX', 'size' : 16 }, + '/vexw' : { 'label' : 'UD_TAB__OPC_VEX_W', 'size' : 2 }, + '/vexl' : { 'label' : 'UD_TAB__OPC_VEX_L', 'size' : 2 }, + } + + + def __init__(self, typ): + assert typ in self._TableInfo + self._typ = typ + self._entries = {} + + + def size(self): + return self._TableInfo[self._typ]['size'] + + def entries(self): + return itemslist(self._entries) - def sizeOfTable( self, t ): - return self.TableInfo[ t ][ 'size' ] + def numEntries(self): + return len(self._entries.keys()) - def nameOfTable( self, t ): - return self.TableInfo[ t ][ 'name' ] + def label(self): + return self._TableInfo[self._typ]['label'] - # - # Updates a table entry: If the entry doesn't exist - # it will create the entry, otherwise, it will walk - # while validating the path. - # - def updateTable( self, table, index, type, meta ): - if not index in table[ 'entries' ]: - table[ 'entries' ][ index ] = { 'type' : type, 'entries' : {}, 'meta' : meta } - if table[ 'entries' ][ index ][ 'type' ] != type: - raise NameError( "error: violation in opcode mapping (overwrite) %s with %s." % - ( table[ 'entries' ][ index ][ 'type' ], type) ) - return table[ 'entries' ][ index ] + def typ(self): + return self._typ - class Insn: - """An abstract type representing an instruction in the opcode map. + def meta(self): + return self._typ + + + def __str__(self): + return "table-%s" % self._typ + + + def add(self, opc, obj): + typ = UdOpcodeTable.getOpcodeTyp(opc) + idx = UdOpcodeTable.getOpcodeIdx(opc) + if self._typ != typ or idx in self._entries: + raise CollisionError() + self._entries[idx] = obj + + + def lookup(self, opc): + typ = UdOpcodeTable.getOpcodeTyp(opc) + idx = UdOpcodeTable.getOpcodeIdx(opc) + if self._typ != typ: + raise UdOpcodeTable.CollisionError("%s <-> %s" % (self._typ, typ)) + return self._entries.get(idx, None) + + + def entryAt(self, index): + """Returns the entry at a given index of the table, + None if there is none. Raises an exception if the + index is out of bounds. """ + if index < self.size(): + return self._entries.get(index, None) + raise self.IndexError("index out of bounds: %s" % index) - # A mapping of opcode extensions to their representational - # values used in the opcode map. - OpcExtMap = { - '/rm' : lambda v: "%02x" % int(v, 16), - '/x87' : lambda v: "%02x" % int(v, 16), - '/3dnow' : lambda v: "%02x" % int(v, 16), - '/reg' : lambda v: "%02x" % int(v, 16), - # modrm.mod - # (!11, 11) => (00, 01) - '/mod' : lambda v: '00' if v == '!11' else '01', - # Mode extensions: - # (16, 32, 64) => (00, 01, 02) - '/o' : lambda v: "%02x" % (int(v) / 32), - '/a' : lambda v: "%02x" % (int(v) / 32), - '/m' : lambda v: "%02x" % (int(v) / 32), - '/sse' : lambda v: UdOpcodeTables.OpcExtIndex['sse'][v] - } + def setEntryAt(self, index, obj): + if index < self.size(): + self._entries[index] = obj + else: + raise self.IndexError("index out of bounds: %s" % index) + + @classmethod + def getOpcodeTyp(cls, opc): + if opc.startswith('/'): + return opc.split('=')[0] + else: + return 'opctbl' + + + @classmethod + def getOpcodeIdx(cls, opc): + if opc.startswith('/'): + typ, v = opc.split('=') + return cls.OpcExtMap[typ](v) + else: + # plain opctbl opcode + return int(opc, 16) + + + @classmethod + def getLabels(cls): + """Returns a list of all labels""" + return [cls._TableInfo[k]['label'] for k in cls._TableInfo.keys()] + + +class UdOpcodeTables(object): + """Collection of opcode tables + """ + + class CollisionError(Exception): + def __init__(self, obj1, obj2): + self.obj1, self.obj2 = obj1, obj2 + + def newTable(self, typ): + """Create a new opcode table of a give type `typ`. """ + tbl = UdOpcodeTable(typ) + self._tables.append(tbl) + return tbl + + def mkTrie(self, opcodes, obj): + """Recursively contruct a trie entry mapping a string of + opcodes to an object. + """ + if len(opcodes) == 0: + return obj + opc = opcodes[0] + tbl = self.newTable(UdOpcodeTable.getOpcodeTyp(opc)) + tbl.add(opc, self.mkTrie(opcodes[1:], obj)) + return tbl + + def walk(self, tbl, opcodes): + """Walk down the opcode trie, starting at a given opcode + table, given a string of opcodes. Return None if unable + to walk, the object at the leaf otherwise. + """ + opc = opcodes[0] + e = tbl.lookup(opc) + if e is None: + return None + elif isinstance(e, UdOpcodeTable) and len(opcodes[1:]): + return self.walk(e, opcodes[1:]) + return e + + def map(self, tbl, opcodes, obj): + """Create a mapping from a given string of opcodes to an + object in the opcode trie. Constructs trie branches as + needed. + """ + opc = opcodes[0] + e = tbl.lookup(opc) + if e is None: + tbl.add(opc, self.mkTrie(opcodes[1:], obj)) + else: + if len(opcodes[1:]) == 0: + raise self.CollisionError(e, obj) + self.map(e, opcodes[1:], obj) + + def __init__(self, xml): + self._tables = [] + self._insns = [] + self._mnemonics = {} - def __init__(self, prefixes, mnemonic, opcodes, operands, vendor): - self.opcodes = opcodes - self.prefixes = prefixes - self.mnemonic = mnemonic - self.operands = operands - self.vendor = vendor - self.opcext = {} - - ssePrefix = None - if self.opcodes[0] in ('ssef2', 'ssef3', 'sse66'): - ssePrefix = self.opcodes[0][3:] - self.opcodes.pop(0) - - # do some preliminary decoding of the instruction type - # 1byte, 2byte or 3byte instruction? - self.nByteInsn = 1 - if self.opcodes[0] == '0f': # 2byte - # 2+ byte opcodes are always disambiguated by an - # sse prefix, unless it is a 3d now instruction - # which is 0f 0f ... - if self.opcodes[1] != '0f' and ssePrefix is None: - ssePrefix = 'none' - if self.opcodes[1] in ('38', '3a'): # 3byte - self.nByteInsn = 3 + # The root table is always a 256 entry opctbl, indexed + # by a plain opcode byte + self.root = self.newTable('opctbl') + + if os.getenv("UD_OPCODE_DEBUG"): + self._logFh = open("opcodeTables.log", "w") + + # add an invalid instruction entry without any mapping + # in the opcode tables. + self.invalidInsn = UdInsnDef(mnemonic="invalid", opcodes=[], cpuid=[], + operands=[], prefixes=[]) + self._insns.append(self.invalidInsn) + + # Construct UdOpcodeTables object from the given + # udis86 optable.xml + for insn in self.__class__.parseOptableXML(xml): + self.addInsnDef(insn) + self.patchAvx2byte() + self.mergeSSENONE() + self.printStats() + + def log(self, s): + if os.getenv("UD_OPCODE_DEBUG"): + self._logFh.write(s + "\n") + + + def mergeSSENONE(self): + """Merge sse tables with only one entry for /sse=none + """ + for table in self._tables: + for k, e in table.entries(): + if isinstance(e, UdOpcodeTable) and e.typ() == '/sse': + if e.numEntries() == 1: + sse = e.lookup("/sse=none") + if sse: + table.setEntryAt(k, sse) + uniqTables = {} + def genTableList(tbl): + if tbl not in uniqTables: + self._tables.append(tbl) + uniqTables[tbl] = 1 + for k, e in tbl.entries(): + if isinstance(e, UdOpcodeTable): + genTableList(e) + self._tables = [] + genTableList(self.root) + + + def patchAvx2byte(self): + # create avx tables + for pp in (None, 'f2', 'f3', '66'): + for m in (None, '0f', '0f38', '0f3a'): + if pp is None and m is None: + continue + if pp is None: + vex = m + elif m is None: + vex = pp else: - self.nByteInsn = 2 - - # The opcode that indexes into the opcode table. - self.opcode = self.opcodes[self.nByteInsn - 1] - - # Record opcode extensions - for opcode in self.opcodes[self.nByteInsn:]: - arg, val = opcode.split('=') - self.opcext[arg] = self.OpcExtMap[arg](val) - - # Record sse extension: the reason sse extension is handled - # separately is that historically sse was handled as a first - # class opcode, not as an extension. Now that sse is handled - # as an extension, we do the manual conversion here, as opposed - # to modifying the opcode xml file. - if ssePrefix is not None: - self.opcext['/sse'] = self.OpcExtMap['/sse'](ssePrefix) - - def parse(self, table, insn): - index = insn.opcodes[0]; - if insn.nByteInsn > 1: - assert index == '0f' - table = self.updateTable(table, index, 'opctbl', '0f') - index = insn.opcodes[1] - - if insn.nByteInsn == 3: - table = self.updateTable(table, index, 'opctbl', index) - index = insn.opcodes[2] - - # Walk down the tree, create levels as needed, for opcode - # extensions. The order is important, and determines how + vex = pp + '_' + m + table = self.walk(self.root, ('c4', '/vex=' + vex)) + self.map(self.root, ('c5', '/vex=' + vex), table) + + + def addInsn(self, **insnDef): + + # Canonicalize opcode list + opcexts = insnDef['opcexts'] + opcodes = list(insnDef['opcodes']) + + # Re-order vex + if '/vex' in opcexts: + assert opcodes[0] == 'c4' or opcodes[0] == 'c5' + opcodes.insert(1, '/vex=' + opcexts['/vex']) + + # Add extensions. The order is important, and determines how # well the opcode table is packed. Also note, /sse must be # before /o, because /sse may consume operand size prefix # affect the outcome of /o. - for ext in ('/mod', '/x87', '/reg', '/rm', '/sse', - '/o', '/a', '/m', '/3dnow'): - if ext in insn.opcext: - table = self.updateTable(table, index, ext, ext) - index = insn.opcext[ext] - - # additional table for disambiguating vendor - if len(insn.vendor): - table = self.updateTable(table, index, 'vendor', insn.vendor) - index = self.OpcExtIndex['vendor'][insn.vendor] - - # make leaf node entries - leaf = self.updateTable(table, index, 'insn', '') - - leaf['mnemonic'] = insn.mnemonic - leaf['prefixes'] = insn.prefixes - leaf['operands'] = insn.operands - - # add instruction to linear table of instruction forms - self.InsnTable.append({ 'prefixes' : insn.prefixes, - 'mnemonic' : insn.mnemonic, - 'operands' : insn.operands }) - - # add mnemonic to mnemonic table - if not insn.mnemonic in self.MnemonicsTable: - self.MnemonicsTable.append(insn.mnemonic) - - - # Adds an instruction definition to the opcode tables - def addInsnDef( self, prefixes, mnemonic, opcodes, operands, vendor ): - insn = self.Insn(prefixes=prefixes, - mnemonic=mnemonic, - opcodes=opcodes, - operands=operands, - vendor=vendor) - self.parse(self.OpcodeTable0, insn) - - def print_table( self, table, pfxs ): - print("%s |" % pfxs) - keys = table[ 'entries' ].keys() - if ( len( keys ) ): - keys.sort() - for idx in keys: - e = table[ 'entries' ][ idx ] - if e[ 'type' ] == 'insn': - print("%s |-<%s>" % ( pfxs, idx )), - print("%s %s" % ( e[ 'mnemonic' ], ' '.join( e[ 'operands'] ))) + for ext in ('/mod', '/x87', '/reg', '/rm', '/sse', '/o', '/a', '/m', + '/vexw', '/vexl', '/3dnow', '/vendor'): + if ext in opcexts: + opcodes.append(ext + '=' + opcexts[ext]) + + insn = UdInsnDef(mnemonic = insnDef['mnemonic'], + prefixes = insnDef['prefixes'], + operands = insnDef['operands'], + opcodes = opcodes, + cpuid = insnDef['cpuid']) + try: + self.map(self.root, opcodes, insn) + except self.CollisionError as e: + self.pprint() + print(opcodes, insn, str(e.obj1), str(e.obj2)) + raise + except Exception as e: + self.pprint() + raise + self._insns.append(insn) + # add to lookup by mnemonic structure + if insn.mnemonic not in self._mnemonics: + self._mnemonics[insn.mnemonic] = [ insn ] + else: + self._mnemonics[insn.mnemonic].append(insn) + + + def addInsnDef(self, insnDef): + opcodes = [] + opcexts = {} + + # pack plain opcodes first, and collect opcode + # extensions + for opc in insnDef['opcodes']: + if not opc.startswith('/'): + opcodes.append(opc) else: - print("%s |-<%s> %s" % ( pfxs, idx, e['type'] )) - self.print_table( e, pfxs + ' |' ) + e, v = opc.split('=') + opcexts[e] = v + + # treat vendor as an opcode extension + if len(insnDef['vendor']): + opcexts['/vendor'] = insnDef['vendor'][0] + + if insnDef['mnemonic'] in ('lds', 'les'): + # + # Massage lds and les, which share the same prefix as AVX + # instructions, to work well with the opcode tree. + # + opcexts['/vex'] = 'none' + elif '/vex' in opcexts: + # A proper avx instruction definition; make sure there are + # no legacy opcode extensions + assert '/sse' not in opcodes + + # make sure the opcode definitions don't already include + # the avx prefixes. + assert opcodes[0] not in ('c4', 'c5') + + # An avx only instruction is defined by the /vex= opcode + # extension. They do not include the c4 (long form) or + # c5 (short form) prefix. As part of opcode table generate, + # here we create the long form definition, and then patch + # the table for c5 in a later stage. + # Construct a long-form definition of the avx instruction + opcodes.insert(0, 'c4') + elif (opcodes[0] == '0f' and opcodes[1] != '0f' and + '/sse' not in opcexts): + # Make all 2-byte opcode form isntructions play nice with sse + # opcode maps. + opcexts['/sse'] = 'none' + + # legacy sse defs that get promoted to avx + fn = self.addInsn + if 'avx' in insnDef['cpuid'] and '/sse' in opcexts: + fn = self.addSSE2AVXInsn + + fn(mnemonic = insnDef['mnemonic'], + prefixes = insnDef['prefixes'], + opcodes = opcodes, + opcexts = opcexts, + operands = insnDef['operands'], + cpuid = insnDef['cpuid']) + + + def addSSE2AVXInsn(self, **insnDef): + """Add an instruction definition containing an avx cpuid bit, but + declared in its legacy SSE form. The function splits the + definition to create two new definitions, one for SSE and one + promoted to an AVX form. + """ + + # SSE + ssemnemonic = insnDef['mnemonic'] + sseopcodes = insnDef['opcodes'] + # remove vex opcode extensions + sseopcexts = dict([(e, v) for e, v in itemslist(insnDef['opcexts']) + if not e.startswith('/vex')]) + # strip out avx operands, preserving relative ordering + # of remaining operands + sseoperands = [opr for opr in insnDef['operands'] + if opr not in ('H', 'L')] + # strip out avx prefixes + sseprefixes = [pfx for pfx in insnDef['prefixes'] + if not pfx.startswith('vex')] + # strip out avx bits from cpuid + ssecpuid = [flag for flag in insnDef['cpuid'] + if not flag.startswith('avx')] + + self.addInsn(mnemonic = ssemnemonic, + prefixes = sseprefixes, + opcodes = sseopcodes, + opcexts = sseopcexts, + operands = sseoperands, + cpuid = ssecpuid) + + # AVX + vexmnemonic = 'v' + insnDef['mnemonic'] + vexprefixes = insnDef['prefixes'] + vexopcodes = ['c4'] + vexopcexts = dict([(e, insnDef['opcexts'][e]) + for e in insnDef['opcexts'] if e != '/sse']) + vexopcexts['/vex'] = insnDef['opcexts']['/sse'] + '_' + '0f' + if insnDef['opcodes'][1] == '38' or insnDef['opcodes'][1] == '3a': + vexopcexts['/vex'] += insnDef['opcodes'][1] + vexopcodes.extend(insnDef['opcodes'][2:]) + else: + vexopcodes.extend(insnDef['opcodes'][1:]) + vexoperands = [] + for o in insnDef['operands']: + # make the operand size explicit: x + if o in ('V', 'W', 'H', 'U'): + o = o + 'x' + vexoperands.append(o) + vexcpuid = [flag for flag in insnDef['cpuid'] + if not flag.startswith('sse')] + + self.addInsn(mnemonic = vexmnemonic, + prefixes = vexprefixes, + opcodes = vexopcodes, + opcexts = vexopcexts, + operands = vexoperands, + cpuid = vexcpuid) + + def getInsnList(self): + """Returns a list of all instructions in the collection""" + return self._insns + + + def getTableList(self): + """Returns a list of all tables in the collection""" + return self._tables + + def getMnemonicsList(self): + """Returns a sorted list of mnemonics""" + return sorted(self._mnemonics.keys()) + + + def pprint(self): + def printWalk(tbl, indent=""): + entries = tbl.entries() + for k, e in entries: + if isinstance(e, UdOpcodeTable): + self.log("%s |-<%02x> %s" % (indent, k, e)) + printWalk(e, indent + " |") + elif isinstance(e, UdInsnDef): + self.log("%s |-<%02x> %s" % (indent, k, e)) + printWalk(self.root) + + + def printStats(self): + tables = self.getTableList() + self.log("stats: ") + self.log(" Num tables = %d" % len(tables)) + self.log(" Num insnDefs = %d" % len(self.getInsnList())) + self.log(" Num insns = %d" % len(self.getMnemonicsList())) + + totalSize = 0 + totalEntries = 0 + for table in tables: + totalSize += table.size() + totalEntries += table.numEntries() + self.log(" Packing Ratio = %d%%" % ((totalEntries * 100) / totalSize)) + self.log("--------------------") + + self.pprint() + + + @staticmethod + def parseOptableXML(xml): + """Parse udis86 optable.xml file and return list of + instruction definitions. + """ + from xml.dom import minidom + + xmlDoc = minidom.parse(xml) + tlNode = xmlDoc.firstChild + insns = [] + + while tlNode and tlNode.localName != "x86optable": + tlNode = tlNode.nextSibling + + for insnNode in tlNode.childNodes: + if not insnNode.localName: + continue + if insnNode.localName != "instruction": + raise Exception("warning: invalid insn node - %s" % insnNode.localName) + mnemonic = insnNode.getElementsByTagName('mnemonic')[0].firstChild.data + vendor, cpuid = '', [] + + for node in insnNode.childNodes: + if node.localName == 'vendor': + vendor = node.firstChild.data.split() + elif node.localName == 'cpuid': + cpuid = node.firstChild.data.split() - def print_tree( self ): - self.print_table( self.OpcodeTable0, '' ) + for node in insnNode.childNodes: + if node.localName == 'def': + insnDef = { 'pfx' : [] } + for node in node.childNodes: + if not node.localName: + continue + if node.localName in ('pfx', 'opc', 'opr', 'vendor', 'cpuid'): + insnDef[node.localName] = node.firstChild.data.split() + elif node.localName == 'mode': + insnDef['pfx'].extend(node.firstChild.data.split()) + insns.append({'prefixes' : insnDef.get('pfx', []), + 'mnemonic' : mnemonic, + 'opcodes' : insnDef.get('opc', []), + 'operands' : insnDef.get('opr', []), + 'vendor' : insnDef.get('vendor', vendor), + 'cpuid' : insnDef.get('cpuid', cpuid)}) + return insns diff --git a/Source/JavaScriptCore/disassembler/udis86/ud_optable.py b/Source/JavaScriptCore/disassembler/udis86/ud_optable.py deleted file mode 100644 index 0350643fd..000000000 --- a/Source/JavaScriptCore/disassembler/udis86/ud_optable.py +++ /dev/null @@ -1,103 +0,0 @@ -# udis86 - scripts/ud_optable.py (optable.xml parser) -# -# Copyright (c) 2009 Vivek Thampi -# All rights reserved. -# -# Redistribution and use in source and binary forms, with or without modification, -# are permitted provided that the following conditions are met: -# -# * Redistributions of source code must retain the above copyright notice, -# this list of conditions and the following disclaimer. -# * Redistributions in binary form must reproduce the above copyright notice, -# this list of conditions and the following disclaimer in the documentation -# and/or other materials provided with the distribution. -# -# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND -# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED -# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE -# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR -# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES -# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; -# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON -# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -import os -import sys -from xml.dom import minidom - -class UdOptableXmlParser: - - def parseDef( self, node ): - ven = '' - pfx = [] - opc = [] - opr = [] - for def_node in node.childNodes: - if not def_node.localName: - continue - if def_node.localName == 'pfx': - pfx = def_node.firstChild.data.split(); - elif def_node.localName == 'opc': - opc = def_node.firstChild.data.split(); - elif def_node.localName == 'opr': - opr = def_node.firstChild.data.split(); - elif def_node.localName == 'mode': - pfx.extend( def_node.firstChild.data.split() ); - elif def_node.localName == 'syn': - pfx.extend( def_node.firstChild.data.split() ); - elif def_node.localName == 'vendor': - ven = ( def_node.firstChild.data ); - else: - print("warning: invalid node - %s" % def_node.localName) - continue - return ( pfx, opc, opr, ven ) - - def parse( self, xml, fn ): - xmlDoc = minidom.parse( xml ) - self.TlNode = xmlDoc.firstChild - - while self.TlNode and self.TlNode.localName != "x86optable": - self.TlNode = self.TlNode.nextSibling - - for insnNode in self.TlNode.childNodes: - if not insnNode.localName: - continue - if insnNode.localName != "instruction": - print("warning: invalid insn node - %s" % insnNode.localName) - continue - - mnemonic = insnNode.getElementsByTagName( 'mnemonic' )[ 0 ].firstChild.data - vendor = '' - - for node in insnNode.childNodes: - if node.localName == 'vendor': - vendor = node.firstChild.data - elif node.localName == 'def': - ( prefixes, opcodes, operands, local_vendor ) = \ - self.parseDef( node ) - if ( len( local_vendor ) ): - vendor = local_vendor - # callback - fn( prefixes, mnemonic, opcodes, operands, vendor ) - - -def printFn( pfx, mnm, opc, opr, ven ): - print('def: '), - if len( pfx ): - print(' '.join( pfx )), - print("%s %s %s %s" % \ - ( mnm, ' '.join( opc ), ' '.join( opr ), ven )) - - -def parse( xml, callback ): - parser = UdOptableXmlParser() - parser.parse( xml, callback ) - -def main(): - parser = UdOptableXmlParser() - parser.parse( sys.argv[ 1 ], printFn ) - -if __name__ == "__main__": - main() diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86.c b/Source/JavaScriptCore/disassembler/udis86/udis86.c index 264103423..489f9b8ad 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86.c +++ b/Source/JavaScriptCore/disassembler/udis86/udis86.c @@ -1,6 +1,6 @@ /* udis86 - libudis86/udis86.c * - * Copyright (c) 2002-2009 Vivek Thampi + * Copyright (c) 2002-2013 Vivek Thampi * All rights reserved. * * Redistribution and use in source and binary forms, with or without modification, @@ -28,16 +28,19 @@ #if USE(UDIS86) -#include "udis86_input.h" +#include "udis86_udint.h" #include "udis86_extern.h" +#include "udis86_decode.h" -#ifndef __UD_STANDALONE__ -# include -# include -#endif /* __UD_STANDALONE__ */ +#if !defined(__UD_STANDALONE__) +#include +#endif /* !__UD_STANDALONE__ */ + +static void ud_inp_init(struct ud *u); /* ============================================================================= - * ud_init() - Initializes ud_t object. + * ud_init + * Initializes ud_t object. * ============================================================================= */ extern void @@ -50,30 +53,34 @@ ud_init(struct ud* u) #ifndef __UD_STANDALONE__ ud_set_input_file(u, stdin); #endif /* __UD_STANDALONE__ */ + + ud_set_asm_buffer(u, u->asm_buf_int, sizeof(u->asm_buf_int)); } + /* ============================================================================= - * ud_disassemble() - disassembles one instruction and returns the number of - * bytes disassembled. A zero means end of disassembly. + * ud_disassemble + * Disassembles one instruction and returns the number of + * bytes disassembled. A zero means end of disassembly. * ============================================================================= */ extern unsigned int ud_disassemble(struct ud* u) { - if (ud_input_end(u)) - return 0; - - - u->insn_buffer[0] = u->insn_hexcode[0] = 0; - - - if (ud_decode(u) == 0) - return 0; - if (u->translator) - u->translator(u); - return ud_insn_len(u); + int len; + if (u->inp_end) { + return 0; + } + if ((len = ud_decode(u)) > 0) { + if (u->translator != NULL) { + u->asm_buf[0] = '\0'; + u->translator(u); + } + } + return len; } + /* ============================================================================= * ud_set_mode() - Set Disassemly Mode. * ============================================================================= @@ -82,10 +89,10 @@ extern void ud_set_mode(struct ud* u, uint8_t m) { switch(m) { - case 16: - case 32: - case 64: u->dis_mode = m ; return; - default: u->dis_mode = 16; return; + case 16: + case 32: + case 64: u->dis_mode = m ; return; + default: u->dis_mode = 16; return; } } @@ -97,14 +104,14 @@ extern void ud_set_vendor(struct ud* u, unsigned v) { switch(v) { - case UD_VENDOR_INTEL: - u->vendor = v; - break; - case UD_VENDOR_ANY: - u->vendor = v; - break; - default: - u->vendor = UD_VENDOR_AMD; + case UD_VENDOR_INTEL: + u->vendor = v; + break; + case UD_VENDOR_ANY: + u->vendor = v; + break; + default: + u->vendor = UD_VENDOR_AMD; } } @@ -132,18 +139,18 @@ ud_set_syntax(struct ud* u, void (*t)(struct ud*)) * ud_insn() - returns the disassembled instruction * ============================================================================= */ -extern char* -ud_insn_asm(struct ud* u) +const char* +ud_insn_asm(const struct ud* u) { - return u->insn_buffer; + return u->asm_buf; } /* ============================================================================= * ud_insn_offset() - Returns the offset. * ============================================================================= */ -extern uint64_t -ud_insn_off(struct ud* u) +uint64_t +ud_insn_off(const struct ud* u) { return u->insn_offset; } @@ -153,30 +160,303 @@ ud_insn_off(struct ud* u) * ud_insn_hex() - Returns hex form of disassembled instruction. * ============================================================================= */ -extern char* +const char* ud_insn_hex(struct ud* u) { + u->insn_hexcode[0] = 0; + if (!u->error) { + unsigned int i; + const unsigned char *src_ptr = ud_insn_ptr(u); + char* src_hex = (char*) u->insn_hexcode; + char* const src_hex_base = src_hex; + /* for each byte used to decode instruction */ + for (i = 0; i < ud_insn_len(u) && i < sizeof(u->insn_hexcode) / 2; + ++i, ++src_ptr) { + snprintf(src_hex, sizeof(u->insn_hexcode) - (src_hex - src_hex_base), "%02x", *src_ptr & 0xFF); + src_hex += 2; + } + } return u->insn_hexcode; } + /* ============================================================================= - * ud_insn_ptr() - Returns code disassembled. + * ud_insn_ptr + * Returns a pointer to buffer containing the bytes that were + * disassembled. * ============================================================================= */ -extern uint8_t* -ud_insn_ptr(struct ud* u) +extern const uint8_t* +ud_insn_ptr(const struct ud* u) { - return u->inp_sess; + return (u->inp_buf == NULL) ? + u->inp_sess : u->inp_buf + (u->inp_buf_index - u->inp_ctr); } + /* ============================================================================= - * ud_insn_len() - Returns the count of bytes disassembled. + * ud_insn_len + * Returns the count of bytes disassembled. * ============================================================================= */ extern unsigned int -ud_insn_len(struct ud* u) +ud_insn_len(const struct ud* u) { return u->inp_ctr; } + +/* ============================================================================= + * ud_insn_get_opr + * Return the operand struct representing the nth operand of + * the currently disassembled instruction. Returns NULL if + * there's no such operand. + * ============================================================================= + */ +const struct ud_operand* +ud_insn_opr(const struct ud *u, unsigned int n) +{ + if (n > 3 || u->operand[n].type == UD_NONE) { + return NULL; + } else { + return &u->operand[n]; + } +} + + +/* ============================================================================= + * ud_opr_is_sreg + * Returns non-zero if the given operand is of a segment register type. + * ============================================================================= + */ +int +ud_opr_is_sreg(const struct ud_operand *opr) +{ + return opr->type == UD_OP_REG && + opr->base >= UD_R_ES && + opr->base <= UD_R_GS; +} + + +/* ============================================================================= + * ud_opr_is_sreg + * Returns non-zero if the given operand is of a general purpose + * register type. + * ============================================================================= + */ +int +ud_opr_is_gpr(const struct ud_operand *opr) +{ + return opr->type == UD_OP_REG && + opr->base >= UD_R_AL && + opr->base <= UD_R_R15; +} + + +/* ============================================================================= + * ud_set_user_opaque_data + * ud_get_user_opaque_data + * Get/set user opaqute data pointer + * ============================================================================= + */ +void +ud_set_user_opaque_data(struct ud * u, void* opaque) +{ + u->user_opaque_data = opaque; +} + +void* +ud_get_user_opaque_data(const struct ud *u) +{ + return u->user_opaque_data; +} + + +/* ============================================================================= + * ud_set_asm_buffer + * Allow the user to set an assembler output buffer. If `buf` is NULL, + * we switch back to the internal buffer. + * ============================================================================= + */ +void +ud_set_asm_buffer(struct ud *u, char *buf, size_t size) +{ + if (buf == NULL) { + ud_set_asm_buffer(u, u->asm_buf_int, sizeof(u->asm_buf_int)); + } else { + u->asm_buf = buf; + u->asm_buf_size = size; + } +} + + +/* ============================================================================= + * ud_set_sym_resolver + * Set symbol resolver for relative targets used in the translation + * phase. + * + * The resolver is a function that takes a uint64_t address and returns a + * symbolic name for the that address. The function also takes a second + * argument pointing to an integer that the client can optionally set to a + * non-zero value for offsetted targets. (symbol+offset) The function may + * also return NULL, in which case the translator only prints the target + * address. + * + * The function pointer maybe NULL which resets symbol resolution. + * ============================================================================= + */ +void +ud_set_sym_resolver(struct ud *u, const char* (*resolver)(struct ud*, + uint64_t addr, + int64_t *offset)) +{ + u->sym_resolver = resolver; +} + + +/* ============================================================================= + * ud_insn_mnemonic + * Return the current instruction mnemonic. + * ============================================================================= + */ +enum ud_mnemonic_code +ud_insn_mnemonic(const struct ud *u) +{ + return u->mnemonic; +} + + +/* ============================================================================= + * ud_lookup_mnemonic + * Looks up mnemonic code in the mnemonic string table. + * Returns NULL if the mnemonic code is invalid. + * ============================================================================= + */ +const char* +ud_lookup_mnemonic(enum ud_mnemonic_code c) +{ + if (c < UD_MAX_MNEMONIC_CODE) { + return ud_mnemonics_str[c]; + } else { + return NULL; + } +} + + +/* + * ud_inp_init + * Initializes the input system. + */ +static void +ud_inp_init(struct ud *u) +{ + u->inp_hook = NULL; + u->inp_buf = NULL; + u->inp_buf_size = 0; + u->inp_buf_index = 0; + u->inp_curr = 0; + u->inp_ctr = 0; + u->inp_end = 0; + u->inp_peek = UD_EOI; + UD_NON_STANDALONE(u->inp_file = NULL); +} + + +/* ============================================================================= + * ud_inp_set_hook + * Sets input hook. + * ============================================================================= + */ +void +ud_set_input_hook(register struct ud* u, int (*hook)(struct ud*)) +{ + ud_inp_init(u); + u->inp_hook = hook; +} + +/* ============================================================================= + * ud_inp_set_buffer + * Set buffer as input. + * ============================================================================= + */ +void +ud_set_input_buffer(register struct ud* u, const uint8_t* buf, size_t len) +{ + ud_inp_init(u); + u->inp_buf = buf; + u->inp_buf_size = len; + u->inp_buf_index = 0; +} + + +#ifndef __UD_STANDALONE__ +/* ============================================================================= + * ud_input_set_file + * Set FILE as input. + * ============================================================================= + */ +static int +inp_file_hook(struct ud* u) +{ + return fgetc(u->inp_file); +} + +void +ud_set_input_file(register struct ud* u, FILE* f) +{ + ud_inp_init(u); + u->inp_hook = inp_file_hook; + u->inp_file = f; +} +#endif /* __UD_STANDALONE__ */ + + +/* ============================================================================= + * ud_input_skip + * Skip n input bytes. + * ============================================================================ + */ +void +ud_input_skip(struct ud* u, size_t n) +{ + if (u->inp_end) { + return; + } + if (u->inp_buf == NULL) { + while (n--) { + int c = u->inp_hook(u); + if (c == UD_EOI) { + goto eoi; + } + } + return; + } else { + if (n > u->inp_buf_size || + u->inp_buf_index > u->inp_buf_size - n) { + u->inp_buf_index = u->inp_buf_size; + goto eoi; + } + u->inp_buf_index += n; + return; + } +eoi: + u->inp_end = 1; + UDERR(u, "cannot skip, eoi received\b"); + return; +} + + +/* ============================================================================= + * ud_input_end + * Returns non-zero on end-of-input. + * ============================================================================= + */ +int +ud_input_end(const struct ud *u) +{ + return u->inp_end; +} + #endif // USE(UDIS86) + +/* vim:set ts=2 sw=2 expandtab */ diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_decode.c b/Source/JavaScriptCore/disassembler/udis86/udis86_decode.c index 579903642..c0ea28362 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_decode.c +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_decode.c @@ -28,14 +28,10 @@ #if USE(UDIS86) -#include "udis86_extern.h" +#include "udis86_udint.h" #include "udis86_types.h" -#include "udis86_input.h" +#include "udis86_extern.h" #include "udis86_decode.h" -#include - -#define dbg(x, n...) -/* #define dbg printf */ #ifndef __UD_STANDALONE__ # include @@ -44,15 +40,164 @@ /* The max number of prefixes to an instruction */ #define MAX_PREFIXES 15 -/* instruction aliases and special cases */ -static struct ud_itab_entry s_ie__invalid = - { UD_Iinvalid, O_NONE, O_NONE, O_NONE, P_none }; +/* rex prefix bits */ +#define REX_W(r) ( ( 0xF & ( r ) ) >> 3 ) +#define REX_R(r) ( ( 0x7 & ( r ) ) >> 2 ) +#define REX_X(r) ( ( 0x3 & ( r ) ) >> 1 ) +#define REX_B(r) ( ( 0x1 & ( r ) ) >> 0 ) +#define REX_PFX_MASK(n) ( ( P_REXW(n) << 3 ) | \ + ( P_REXR(n) << 2 ) | \ + ( P_REXX(n) << 1 ) | \ + ( P_REXB(n) << 0 ) ) + +/* scable-index-base bits */ +#define SIB_S(b) ( ( b ) >> 6 ) +#define SIB_I(b) ( ( ( b ) >> 3 ) & 7 ) +#define SIB_B(b) ( ( b ) & 7 ) + +/* modrm bits */ +#define MODRM_REG(b) ( ( ( b ) >> 3 ) & 7 ) +#define MODRM_NNN(b) ( ( ( b ) >> 3 ) & 7 ) +#define MODRM_MOD(b) ( ( ( b ) >> 6 ) & 3 ) +#define MODRM_RM(b) ( ( b ) & 7 ) + +static int decode_ext(struct ud *u, uint16_t ptr); +static int decode_opcode(struct ud *u); + +enum reg_class { /* register classes */ + REGCLASS_GPR, + REGCLASS_MMX, + REGCLASS_CR, + REGCLASS_DB, + REGCLASS_SEG, + REGCLASS_XMM +}; + + /* + * inp_start + * Should be called before each de-code operation. + */ +static void +inp_start(struct ud *u) +{ + u->inp_ctr = 0; +} -static int -decode_ext(struct ud *u, uint16_t ptr); +static uint8_t +inp_peek(struct ud *u) +{ + if (u->inp_end == 0) { + if (u->inp_buf != NULL) { + if (u->inp_buf_index < u->inp_buf_size) { + return u->inp_buf[u->inp_buf_index]; + } + } else if (u->inp_peek != UD_EOI) { + return u->inp_peek; + } else { + int c; + if ((c = u->inp_hook(u)) != UD_EOI) { + u->inp_peek = c; + return u->inp_peek; + } + } + } + u->inp_end = 1; + UDERR(u, "byte expected, eoi received\n"); + return 0; +} + +static uint8_t +inp_next(struct ud *u) +{ + if (u->inp_end == 0) { + if (u->inp_buf != NULL) { + if (u->inp_buf_index < u->inp_buf_size) { + u->inp_ctr++; + return (u->inp_curr = u->inp_buf[u->inp_buf_index++]); + } + } else { + int c = u->inp_peek; + if (c != UD_EOI || (c = u->inp_hook(u)) != UD_EOI) { + u->inp_peek = UD_EOI; + u->inp_curr = c; + u->inp_sess[u->inp_ctr++] = u->inp_curr; + return u->inp_curr; + } + } + } + u->inp_end = 1; + UDERR(u, "byte expected, eoi received\n"); + return 0; +} +static uint8_t +inp_curr(struct ud *u) +{ + return u->inp_curr; +} + + +/* + * inp_uint8 + * int_uint16 + * int_uint32 + * int_uint64 + * Load little-endian values from input + */ +static uint8_t +inp_uint8(struct ud* u) +{ + return inp_next(u); +} + +static uint16_t +inp_uint16(struct ud* u) +{ + uint16_t r, ret; -static inline int + ret = inp_next(u); + r = inp_next(u); + return ret | (r << 8); +} + +static uint32_t +inp_uint32(struct ud* u) +{ + uint32_t r, ret; + + ret = inp_next(u); + r = inp_next(u); + ret = ret | (r << 8); + r = inp_next(u); + ret = ret | (r << 16); + r = inp_next(u); + return ret | (r << 24); +} + +static uint64_t +inp_uint64(struct ud* u) +{ + uint64_t r, ret; + + ret = inp_next(u); + r = inp_next(u); + ret = ret | (r << 8); + r = inp_next(u); + ret = ret | (r << 16); + r = inp_next(u); + ret = ret | (r << 24); + r = inp_next(u); + ret = ret | (r << 32); + r = inp_next(u); + ret = ret | (r << 40); + r = inp_next(u); + ret = ret | (r << 48); + r = inp_next(u); + return ret | (r << 56); +} + + +static UD_INLINE int eff_opr_mode(int dis_mode, int rex_w, int pfx_opr) { if (dis_mode == 64) { @@ -60,13 +205,13 @@ eff_opr_mode(int dis_mode, int rex_w, int pfx_opr) } else if (dis_mode == 32) { return pfx_opr ? 16 : 32; } else { - ASSERT(dis_mode == 16); + UD_ASSERT(dis_mode == 16); return pfx_opr ? 32 : 16; } } -static inline int +static UD_INLINE int eff_adr_mode(int dis_mode, int pfx_adr) { if (dis_mode == 64) { @@ -74,21 +219,12 @@ eff_adr_mode(int dis_mode, int pfx_adr) } else if (dis_mode == 32) { return pfx_adr ? 16 : 32; } else { - ASSERT(dis_mode == 16); + UD_ASSERT(dis_mode == 16); return pfx_adr ? 32 : 16; } } -/* Looks up mnemonic code in the mnemonic string table - * Returns NULL if the mnemonic code is invalid - */ -const char * ud_lookup_mnemonic( enum ud_mnemonic_code c ) -{ - return ud_mnemonics_str[ c ]; -} - - /* * decode_prefixes * @@ -97,164 +233,128 @@ const char * ud_lookup_mnemonic( enum ud_mnemonic_code c ) static int decode_prefixes(struct ud *u) { - unsigned int have_pfx = 1; - unsigned int i; - uint8_t curr; - - /* if in error state, bail out */ - if ( u->error ) - return -1; - - /* keep going as long as there are prefixes available */ - for ( i = 0; have_pfx ; ++i ) { - - /* Get next byte. */ - ud_inp_next(u); - if ( u->error ) - return -1; - curr = ud_inp_curr( u ); - - /* rex prefixes in 64bit mode */ - if ( u->dis_mode == 64 && ( curr & 0xF0 ) == 0x40 ) { - u->pfx_rex = curr; - } else { - switch ( curr ) - { - case 0x2E : - u->pfx_seg = UD_R_CS; - u->pfx_rex = 0; - break; - case 0x36 : - u->pfx_seg = UD_R_SS; - u->pfx_rex = 0; - break; - case 0x3E : - u->pfx_seg = UD_R_DS; - u->pfx_rex = 0; - break; - case 0x26 : - u->pfx_seg = UD_R_ES; - u->pfx_rex = 0; - break; - case 0x64 : - u->pfx_seg = UD_R_FS; - u->pfx_rex = 0; - break; - case 0x65 : - u->pfx_seg = UD_R_GS; - u->pfx_rex = 0; - break; - case 0x67 : /* adress-size override prefix */ - u->pfx_adr = 0x67; - u->pfx_rex = 0; - break; - case 0xF0 : - u->pfx_lock = 0xF0; - u->pfx_rex = 0; - break; - case 0x66: - /* the 0x66 sse prefix is only effective if no other sse prefix - * has already been specified. - */ - if ( !u->pfx_insn ) u->pfx_insn = 0x66; - u->pfx_opr = 0x66; - u->pfx_rex = 0; - break; - case 0xF2: - u->pfx_insn = 0xF2; - u->pfx_repne = 0xF2; - u->pfx_rex = 0; - break; - case 0xF3: - u->pfx_insn = 0xF3; - u->pfx_rep = 0xF3; - u->pfx_repe = 0xF3; - u->pfx_rex = 0; - break; - default : - /* No more prefixes */ - have_pfx = 0; - break; - } - } - - /* check if we reached max instruction length */ - if ( i + 1 == MAX_INSN_LENGTH ) { - u->error = 1; - break; - } + int done = 0; + uint8_t curr = 0, last = 0; + UD_RETURN_ON_ERROR(u); + + do { + last = curr; + curr = inp_next(u); + UD_RETURN_ON_ERROR(u); + if (u->inp_ctr == MAX_INSN_LENGTH) { + UD_RETURN_WITH_ERROR(u, "max instruction length"); + } + + switch (curr) + { + case 0x2E: + u->pfx_seg = UD_R_CS; + break; + case 0x36: + u->pfx_seg = UD_R_SS; + break; + case 0x3E: + u->pfx_seg = UD_R_DS; + break; + case 0x26: + u->pfx_seg = UD_R_ES; + break; + case 0x64: + u->pfx_seg = UD_R_FS; + break; + case 0x65: + u->pfx_seg = UD_R_GS; + break; + case 0x67: /* adress-size override prefix */ + u->pfx_adr = 0x67; + break; + case 0xF0: + u->pfx_lock = 0xF0; + break; + case 0x66: + u->pfx_opr = 0x66; + break; + case 0xF2: + u->pfx_str = 0xf2; + break; + case 0xF3: + u->pfx_str = 0xf3; + break; + default: + /* consume if rex */ + done = (u->dis_mode == 64 && (curr & 0xF0) == 0x40) ? 0 : 1; + break; } + } while (!done); + /* rex prefixes in 64bit mode, must be the last prefix */ + if (u->dis_mode == 64 && (last & 0xF0) == 0x40) { + u->pfx_rex = last; + } + return 0; +} - /* return status */ - if ( u->error ) - return -1; - /* rewind back one byte in stream, since the above loop - * stops with a non-prefix byte. - */ - ud_inp_back(u); - return 0; +/* + * vex_l, vex_w + * Return the vex.L and vex.W bits + */ +static UD_INLINE uint8_t +vex_l(const struct ud *u) +{ + UD_ASSERT(u->vex_op != 0); + return ((u->vex_op == 0xc4 ? u->vex_b2 : u->vex_b1) >> 2) & 1; } +static UD_INLINE uint8_t +vex_w(const struct ud *u) +{ + UD_ASSERT(u->vex_op != 0); + return u->vex_op == 0xc4 ? ((u->vex_b2 >> 7) & 1) : 0; +} -static inline unsigned int modrm( struct ud * u ) + +static UD_INLINE uint8_t +modrm(struct ud * u) { if ( !u->have_modrm ) { - u->modrm = ud_inp_next( u ); + u->modrm = inp_next( u ); + u->modrm_offset = (uint8_t) (u->inp_ctr - 1); u->have_modrm = 1; } return u->modrm; } -static unsigned int resolve_operand_size( const struct ud * u, unsigned int s ) +static unsigned int +resolve_operand_size(const struct ud* u, ud_operand_size_t osize) { - switch ( s ) - { - case SZ_V: - return ( u->opr_mode ); - case SZ_Z: - return ( u->opr_mode == 16 ) ? 16 : 32; - case SZ_P: - return ( u->opr_mode == 16 ) ? SZ_WP : SZ_DP; - case SZ_MDQ: - return ( u->opr_mode == 16 ) ? 32 : u->opr_mode; - case SZ_RDQ: - return ( u->dis_mode == 64 ) ? 64 : 32; - default: - return s; - } + switch (osize) { + case SZ_V: + return u->opr_mode; + case SZ_Z: + return u->opr_mode == 16 ? 16 : 32; + case SZ_Y: + return u->opr_mode == 16 ? 32 : u->opr_mode; + case SZ_RDQ: + return u->dis_mode == 64 ? 64 : 32; + case SZ_X: + UD_ASSERT(u->vex_op != 0); + return (P_VEXL(u->itab_entry->prefix) && vex_l(u)) ? SZ_QQ : SZ_DQ; + default: + return osize; + } } static int resolve_mnemonic( struct ud* u ) { - /* far/near flags */ - u->br_far = 0; - u->br_near = 0; - /* readjust operand sizes for call/jmp instrcutions */ - if ( u->mnemonic == UD_Icall || u->mnemonic == UD_Ijmp ) { - /* WP: 16:16 pointer */ - if ( u->operand[ 0 ].size == SZ_WP ) { - u->operand[ 0 ].size = 16; - u->br_far = 1; - u->br_near= 0; - /* DP: 32:32 pointer */ - } else if ( u->operand[ 0 ].size == SZ_DP ) { - u->operand[ 0 ].size = 32; - u->br_far = 1; - u->br_near= 0; - } else { - u->br_far = 0; - u->br_near= 1; - } /* resolve 3dnow weirdness. */ - } else if ( u->mnemonic == UD_I3dnow ) { - u->mnemonic = ud_itab[ u->le->table[ ud_inp_curr( u ) ] ].mnemonic; + if ( u->mnemonic == UD_I3dnow ) { + u->mnemonic = ud_itab[ u->le->table[ inp_curr( u ) ] ].mnemonic; } /* SWAPGS is only valid in 64bits mode */ if ( u->mnemonic == UD_Iswapgs && u->dis_mode != 64 ) { - u->error = 1; + UDERR(u, "swapgs invalid in 64bits mode\n"); return -1; } @@ -269,8 +369,8 @@ static int resolve_mnemonic( struct ud* u ) } } - if (u->mnemonic == UD_Inop && u->pfx_rep) { - u->pfx_rep = 0; + if (u->mnemonic == UD_Inop && u->pfx_repe) { + u->pfx_repe = 0; u->mnemonic = UD_Ipause; } return 0; @@ -288,14 +388,14 @@ decode_a(struct ud* u, struct ud_operand *op) /* seg16:off16 */ op->type = UD_OP_PTR; op->size = 32; - op->lval.ptr.off = ud_inp_uint16(u); - op->lval.ptr.seg = ud_inp_uint16(u); + op->lval.ptr.off = inp_uint16(u); + op->lval.ptr.seg = inp_uint16(u); } else { /* seg16:off32 */ op->type = UD_OP_PTR; op->size = 48; - op->lval.ptr.off = ud_inp_uint32(u); - op->lval.ptr.seg = ud_inp_uint16(u); + op->lval.ptr.off = inp_uint32(u); + op->lval.ptr.seg = inp_uint16(u); } } @@ -306,15 +406,11 @@ decode_a(struct ud* u, struct ud_operand *op) static enum ud_type decode_gpr(register struct ud* u, unsigned int s, unsigned char rm) { - s = resolve_operand_size(u, s); - switch (s) { case 64: return UD_R_RAX + rm; - case SZ_DP: case 32: return UD_R_EAX + rm; - case SZ_WP: case 16: return UD_R_AX + rm; case 8: @@ -323,94 +419,103 @@ decode_gpr(register struct ud* u, unsigned int s, unsigned char rm) return UD_R_SPL + (rm-4); return UD_R_AL + rm; } else return UD_R_AL + rm; + case 0: + /* invalid size in case of a decode error */ + UD_ASSERT(u->error); + return UD_NONE; default: - return 0; + UD_ASSERT(!"invalid operand size"); + return UD_NONE; } } -/* ----------------------------------------------------------------------------- - * resolve_gpr64() - 64bit General Purpose Register-Selection. - * ----------------------------------------------------------------------------- - */ -static enum ud_type -resolve_gpr64(struct ud* u, enum ud_operand_code gpr_op, enum ud_operand_size * size) -{ - if (gpr_op >= OP_rAXr8 && gpr_op <= OP_rDIr15) - gpr_op = (gpr_op - OP_rAXr8) | (REX_B(u->pfx_rex) << 3); - else gpr_op = (gpr_op - OP_rAX); - - if (u->opr_mode == 16) { - *size = 16; - return gpr_op + UD_R_AX; - } - if (u->dis_mode == 32 || - (u->opr_mode == 32 && ! (REX_W(u->pfx_rex) || u->default64))) { - *size = 32; - return gpr_op + UD_R_EAX; - } - - *size = 64; - return gpr_op + UD_R_RAX; -} - -/* ----------------------------------------------------------------------------- - * resolve_gpr32 () - 32bit General Purpose Register-Selection. - * ----------------------------------------------------------------------------- - */ -static enum ud_type -resolve_gpr32(struct ud* u, enum ud_operand_code gpr_op) -{ - gpr_op = gpr_op - OP_eAX; - - if (u->opr_mode == 16) - return gpr_op + UD_R_AX; - - return gpr_op + UD_R_EAX; -} - -/* ----------------------------------------------------------------------------- - * resolve_reg() - Resolves the register type - * ----------------------------------------------------------------------------- - */ -static enum ud_type -resolve_reg(struct ud* u, unsigned int type, unsigned char i) +static void +decode_reg(struct ud *u, + struct ud_operand *opr, + int type, + int num, + int size) { + int reg; + size = resolve_operand_size(u, size); switch (type) { - case T_MMX : return UD_R_MM0 + (i & 7); - case T_XMM : return UD_R_XMM0 + i; - case T_CRG : return UD_R_CR0 + i; - case T_DBG : return UD_R_DR0 + i; - case T_SEG : { + case REGCLASS_GPR : reg = decode_gpr(u, size, num); break; + case REGCLASS_MMX : reg = UD_R_MM0 + (num & 7); break; + case REGCLASS_XMM : + reg = num + (size == SZ_QQ ? UD_R_YMM0 : UD_R_XMM0); + break; + case REGCLASS_CR : reg = UD_R_CR0 + num; break; + case REGCLASS_DB : reg = UD_R_DR0 + num; break; + case REGCLASS_SEG : { /* * Only 6 segment registers, anything else is an error. */ - if ((i & 7) > 5) { - u->error = 1; + if ((num & 7) > 5) { + UDERR(u, "invalid segment register value\n"); + return; } else { - return UD_R_ES + (i & 7); + reg = UD_R_ES + (num & 7); } + break; } - case T_NONE: - default: return UD_NONE; + default: + UD_ASSERT(!"invalid register type"); + return; } + opr->type = UD_OP_REG; + opr->base = reg; + opr->size = size; } -/* ----------------------------------------------------------------------------- - * decode_imm() - Decodes Immediate values. - * ----------------------------------------------------------------------------- + +/* + * decode_imm + * + * Decode Immediate values. */ static void -decode_imm(struct ud* u, unsigned int s, struct ud_operand *op) +decode_imm(struct ud* u, unsigned int size, struct ud_operand *op) { - op->size = resolve_operand_size(u, s); + op->size = resolve_operand_size(u, size); op->type = UD_OP_IMM; switch (op->size) { - case 8: op->lval.sbyte = ud_inp_uint8(u); break; - case 16: op->lval.uword = ud_inp_uint16(u); break; - case 32: op->lval.udword = ud_inp_uint32(u); break; - case 64: op->lval.uqword = ud_inp_uint64(u); break; - default: return; + case 8: op->lval.sbyte = inp_uint8(u); break; + case 16: op->lval.uword = inp_uint16(u); break; + case 32: op->lval.udword = inp_uint32(u); break; + case 64: op->lval.uqword = inp_uint64(u); break; + default: return; + } +} + + +/* + * decode_mem_disp + * + * Decode mem address displacement. + */ +static void +decode_mem_disp(struct ud* u, unsigned int size, struct ud_operand *op) +{ + switch (size) { + case 8: + op->offset = 8; + op->lval.ubyte = inp_uint8(u); + break; + case 16: + op->offset = 16; + op->lval.uword = inp_uint16(u); + break; + case 32: + op->offset = 32; + op->lval.udword = inp_uint32(u); + break; + case 64: + op->offset = 64; + op->lval.uqword = inp_uint64(u); + break; + default: + return; } } @@ -421,21 +526,14 @@ decode_imm(struct ud* u, unsigned int s, struct ud_operand *op) * Decodes reg field of mod/rm byte * */ -static void +static UD_INLINE void decode_modrm_reg(struct ud *u, struct ud_operand *operand, unsigned int type, unsigned int size) { - uint8_t reg = (REX_R(u->pfx_rex) << 3) | MODRM_REG(modrm(u)); - operand->type = UD_OP_REG; - operand->size = resolve_operand_size(u, size); - - if (type == T_GPR) { - operand->base = decode_gpr(u, operand->size, reg); - } else { - operand->base = resolve_reg(u, type, reg); - } + uint8_t reg = (REX_R(u->_rex) << 3) | MODRM_REG(modrm(u)); + decode_reg(u, operand, type, reg, size); } @@ -448,67 +546,58 @@ decode_modrm_reg(struct ud *u, static void decode_modrm_rm(struct ud *u, struct ud_operand *op, - unsigned char type, - unsigned int size) + unsigned char type, /* register type */ + unsigned int size) /* operand size */ { - unsigned char mod, rm, reg; + size_t offset = 0; + unsigned char mod, rm; /* get mod, r/m and reg fields */ mod = MODRM_MOD(modrm(u)); - rm = (REX_B(u->pfx_rex) << 3) | MODRM_RM(modrm(u)); - reg = (REX_R(u->pfx_rex) << 3) | MODRM_REG(modrm(u)); - - UNUSED_PARAM(reg); - - op->size = resolve_operand_size(u, size); + rm = (REX_B(u->_rex) << 3) | MODRM_RM(modrm(u)); /* * If mod is 11b, then the modrm.rm specifies a register. * */ if (mod == 3) { - op->type = UD_OP_REG; - if (type == T_GPR) { - op->base = decode_gpr(u, op->size, rm); - } else { - op->base = resolve_reg(u, type, (REX_B(u->pfx_rex) << 3) | (rm & 7)); - } + decode_reg(u, op, type, rm, size); return; - } - + } /* - * !11 => Memory Address + * !11b => Memory Address */ op->type = UD_OP_MEM; + op->size = resolve_operand_size(u, size); if (u->adr_mode == 64) { op->base = UD_R_RAX + rm; if (mod == 1) { - op->offset = 8; + offset = 8; } else if (mod == 2) { - op->offset = 32; + offset = 32; } else if (mod == 0 && (rm & 7) == 5) { op->base = UD_R_RIP; - op->offset = 32; + offset = 32; } else { - op->offset = 0; + offset = 0; } /* * Scale-Index-Base (SIB) */ if ((rm & 7) == 4) { - ud_inp_next(u); + inp_next(u); - op->scale = (1 << SIB_S(ud_inp_curr(u))) & ~1; - op->index = UD_R_RAX + (SIB_I(ud_inp_curr(u)) | (REX_X(u->pfx_rex) << 3)); - op->base = UD_R_RAX + (SIB_B(ud_inp_curr(u)) | (REX_B(u->pfx_rex) << 3)); - + op->base = UD_R_RAX + (SIB_B(inp_curr(u)) | (REX_B(u->_rex) << 3)); + op->index = UD_R_RAX + (SIB_I(inp_curr(u)) | (REX_X(u->_rex) << 3)); /* special conditions for base reference */ if (op->index == UD_R_RSP) { op->index = UD_NONE; op->scale = UD_NONE; + } else { + op->scale = (1 << SIB_S(inp_curr(u))) & ~1; } if (op->base == UD_R_RBP || op->base == UD_R_R13) { @@ -516,32 +605,35 @@ decode_modrm_rm(struct ud *u, op->base = UD_NONE; } if (mod == 1) { - op->offset = 8; + offset = 8; } else { - op->offset = 32; + offset = 32; } } + } else { + op->scale = UD_NONE; + op->index = UD_NONE; } } else if (u->adr_mode == 32) { op->base = UD_R_EAX + rm; if (mod == 1) { - op->offset = 8; + offset = 8; } else if (mod == 2) { - op->offset = 32; + offset = 32; } else if (mod == 0 && rm == 5) { op->base = UD_NONE; - op->offset = 32; + offset = 32; } else { - op->offset = 0; + offset = 0; } /* Scale-Index-Base (SIB) */ if ((rm & 7) == 4) { - ud_inp_next(u); + inp_next(u); - op->scale = (1 << SIB_S(ud_inp_curr(u))) & ~1; - op->index = UD_R_EAX + (SIB_I(ud_inp_curr(u)) | (REX_X(u->pfx_rex) << 3)); - op->base = UD_R_EAX + (SIB_B(ud_inp_curr(u)) | (REX_B(u->pfx_rex) << 3)); + op->scale = (1 << SIB_S(inp_curr(u))) & ~1; + op->index = UD_R_EAX + (SIB_I(inp_curr(u)) | (REX_X(u->pfx_rex) << 3)); + op->base = UD_R_EAX + (SIB_B(inp_curr(u)) | (REX_B(u->pfx_rex) << 3)); if (op->index == UD_R_ESP) { op->index = UD_NONE; @@ -554,11 +646,14 @@ decode_modrm_rm(struct ud *u, op->base = UD_NONE; } if (mod == 1) { - op->offset = 8; + offset = 8; } else { - op->offset = 32; + offset = 32; } } + } else { + op->scale = UD_NONE; + op->index = UD_NONE; } } else { const unsigned int bases[] = { UD_R_BX, UD_R_BX, UD_R_BP, UD_R_BP, @@ -567,58 +662,72 @@ decode_modrm_rm(struct ud *u, UD_NONE, UD_NONE, UD_NONE, UD_NONE }; op->base = bases[rm & 7]; op->index = indices[rm & 7]; + op->scale = UD_NONE; if (mod == 0 && rm == 6) { - op->offset= 16; + offset = 16; op->base = UD_NONE; } else if (mod == 1) { - op->offset = 8; + offset = 8; } else if (mod == 2) { - op->offset = 16; + offset = 16; } } - /* - * extract offset, if any - */ - switch (op->offset) { - case 8 : op->lval.ubyte = ud_inp_uint8(u); break; - case 16: op->lval.uword = ud_inp_uint16(u); break; - case 32: op->lval.udword = ud_inp_uint32(u); break; - case 64: op->lval.uqword = ud_inp_uint64(u); break; - default: break; + if (offset) { + decode_mem_disp(u, offset, op); + } else { + op->offset = 0; } } -/* ----------------------------------------------------------------------------- - * decode_o() - Decodes offset - * ----------------------------------------------------------------------------- + +/* + * decode_moffset + * Decode offset-only memory operand */ -static void -decode_o(struct ud* u, unsigned int s, struct ud_operand *op) +static void +decode_moffset(struct ud *u, unsigned int size, struct ud_operand *opr) { - switch (u->adr_mode) { - case 64: - op->offset = 64; - op->lval.uqword = ud_inp_uint64(u); - break; - case 32: - op->offset = 32; - op->lval.udword = ud_inp_uint32(u); - break; - case 16: - op->offset = 16; - op->lval.uword = ud_inp_uint16(u); - break; - default: - return; - } - op->type = UD_OP_MEM; - op->size = resolve_operand_size(u, s); + opr->type = UD_OP_MEM; + opr->base = UD_NONE; + opr->index = UD_NONE; + opr->scale = UD_NONE; + opr->size = resolve_operand_size(u, size); + decode_mem_disp(u, u->adr_mode, opr); } -/* ----------------------------------------------------------------------------- - * decode_operands() - Disassembles Operands. - * ----------------------------------------------------------------------------- + +static void +decode_vex_vvvv(struct ud *u, struct ud_operand *opr, unsigned size) +{ + uint8_t vvvv; + UD_ASSERT(u->vex_op != 0); + vvvv = ((u->vex_op == 0xc4 ? u->vex_b2 : u->vex_b1) >> 3) & 0xf; + decode_reg(u, opr, REGCLASS_XMM, (0xf & ~vvvv), size); +} + + +/* + * decode_vex_immreg + * Decode source operand encoded in immediate byte [7:4] + */ +static int +decode_vex_immreg(struct ud *u, struct ud_operand *opr, unsigned size) +{ + uint8_t imm = inp_next(u); + uint8_t mask = u->dis_mode == 64 ? 0xf : 0x7; + UD_RETURN_ON_ERROR(u); + UD_ASSERT(u->vex_op != 0); + decode_reg(u, opr, REGCLASS_XMM, mask & (imm >> 4), size); + return 0; +} + + +/* + * decode_operand + * + * Decodes a single operand. + * Returns the type of the operand (UD_NONE if none) */ static int decode_operand(struct ud *u, @@ -626,35 +735,33 @@ decode_operand(struct ud *u, enum ud_operand_code type, unsigned int size) { + operand->type = UD_NONE; + operand->_oprcode = type; + switch (type) { case OP_A : decode_a(u, operand); break; case OP_MR: - if (MODRM_MOD(modrm(u)) == 3) { - decode_modrm_rm(u, operand, T_GPR, - size == SZ_DY ? SZ_MDQ : SZ_V); - } else if (size == SZ_WV) { - decode_modrm_rm( u, operand, T_GPR, SZ_W); - } else if (size == SZ_BV) { - decode_modrm_rm( u, operand, T_GPR, SZ_B); - } else if (size == SZ_DY) { - decode_modrm_rm( u, operand, T_GPR, SZ_D); - } else { - ASSERT(!"unexpected size"); - } + decode_modrm_rm(u, operand, REGCLASS_GPR, + MODRM_MOD(modrm(u)) == 3 ? + Mx_reg_size(size) : Mx_mem_size(size)); break; + case OP_F: + u->br_far = 1; + /* intended fall through */ case OP_M: if (MODRM_MOD(modrm(u)) == 3) { - u->error = 1; + UDERR(u, "expected modrm.mod != 3\n"); } /* intended fall through */ case OP_E: - decode_modrm_rm(u, operand, T_GPR, size); + decode_modrm_rm(u, operand, REGCLASS_GPR, size); break; case OP_G: - decode_modrm_reg(u, operand, T_GPR, size); + decode_modrm_reg(u, operand, REGCLASS_GPR, size); break; + case OP_sI: case OP_I: decode_imm(u, size, operand); break; @@ -662,96 +769,68 @@ decode_operand(struct ud *u, operand->type = UD_OP_CONST; operand->lval.udword = 1; break; - case OP_PR: + case OP_N: if (MODRM_MOD(modrm(u)) != 3) { - u->error = 1; + UDERR(u, "expected modrm.mod == 3\n"); } - decode_modrm_rm(u, operand, T_MMX, size); + /* intended fall through */ + case OP_Q: + decode_modrm_rm(u, operand, REGCLASS_MMX, size); break; case OP_P: - decode_modrm_reg(u, operand, T_MMX, size); + decode_modrm_reg(u, operand, REGCLASS_MMX, size); break; - case OP_VR: + case OP_U: if (MODRM_MOD(modrm(u)) != 3) { - u->error = 1; + UDERR(u, "expected modrm.mod == 3\n"); } /* intended fall through */ case OP_W: - decode_modrm_rm(u, operand, T_XMM, size); + decode_modrm_rm(u, operand, REGCLASS_XMM, size); break; case OP_V: - decode_modrm_reg(u, operand, T_XMM, size); + decode_modrm_reg(u, operand, REGCLASS_XMM, size); break; - case OP_S: - decode_modrm_reg(u, operand, T_SEG, size); + case OP_H: + decode_vex_vvvv(u, operand, size); break; - case OP_AL: - case OP_CL: - case OP_DL: - case OP_BL: - case OP_AH: - case OP_CH: - case OP_DH: - case OP_BH: - operand->type = UD_OP_REG; - operand->base = UD_R_AL + (type - OP_AL); - operand->size = 8; + case OP_MU: + decode_modrm_rm(u, operand, REGCLASS_XMM, + MODRM_MOD(modrm(u)) == 3 ? + Mx_reg_size(size) : Mx_mem_size(size)); break; - case OP_DX: - operand->type = UD_OP_REG; - operand->base = UD_R_DX; - operand->size = 16; + case OP_S: + decode_modrm_reg(u, operand, REGCLASS_SEG, size); break; case OP_O: - decode_o(u, size, operand); + decode_moffset(u, size, operand); break; - case OP_rAXr8: - case OP_rCXr9: - case OP_rDXr10: - case OP_rBXr11: - case OP_rSPr12: - case OP_rBPr13: - case OP_rSIr14: - case OP_rDIr15: - case OP_rAX: - case OP_rCX: - case OP_rDX: - case OP_rBX: - case OP_rSP: - case OP_rBP: - case OP_rSI: - case OP_rDI: - operand->type = UD_OP_REG; - operand->base = resolve_gpr64(u, type, &operand->size); + case OP_R0: + case OP_R1: + case OP_R2: + case OP_R3: + case OP_R4: + case OP_R5: + case OP_R6: + case OP_R7: + decode_reg(u, operand, REGCLASS_GPR, + (REX_B(u->_rex) << 3) | (type - OP_R0), size); break; - case OP_ALr8b: - case OP_CLr9b: - case OP_DLr10b: - case OP_BLr11b: - case OP_AHr12b: - case OP_CHr13b: - case OP_DHr14b: - case OP_BHr15b: { - ud_type_t gpr = (type - OP_ALr8b) + UD_R_AL - + (REX_B(u->pfx_rex) << 3); - if (UD_R_AH <= gpr && u->pfx_rex) { - gpr = gpr + 4; - } - operand->type = UD_OP_REG; - operand->base = gpr; + case OP_AL: + case OP_AX: + case OP_eAX: + case OP_rAX: + decode_reg(u, operand, REGCLASS_GPR, 0, size); break; - } - case OP_eAX: - case OP_eCX: - case OP_eDX: - case OP_eBX: - case OP_eSP: - case OP_eBP: - case OP_eSI: - case OP_eDI: - operand->type = UD_OP_REG; - operand->base = resolve_gpr32(u, type); - operand->size = u->opr_mode == 16 ? 16 : 32; + case OP_CL: + case OP_CX: + case OP_eCX: + decode_reg(u, operand, REGCLASS_GPR, 1, size); + break; + case OP_DL: + case OP_DX: + case OP_eDX: + decode_reg(u, operand, REGCLASS_GPR, 2, size); break; case OP_ES: case OP_CS: @@ -762,7 +841,7 @@ decode_operand(struct ud *u, /* in 64bits mode, only fs and gs are allowed */ if (u->dis_mode == 64) { if (type != OP_FS && type != OP_GS) { - u->error= 1; + UDERR(u, "invalid segment register in 64bits\n"); } } operand->type = UD_OP_REG; @@ -773,17 +852,17 @@ decode_operand(struct ud *u, decode_imm(u, size, operand); operand->type = UD_OP_JIMM; break ; - case OP_Q: - decode_modrm_rm(u, operand, T_MMX, size); - break; case OP_R : - decode_modrm_rm(u, operand, T_GPR, size); + if (MODRM_MOD(modrm(u)) != 3) { + UDERR(u, "expected modrm.mod == 3\n"); + } + decode_modrm_rm(u, operand, REGCLASS_GPR, size); break; case OP_C: - decode_modrm_reg(u, operand, T_CRG, size); + decode_modrm_reg(u, operand, REGCLASS_CR, size); break; case OP_D: - decode_modrm_reg(u, operand, T_DBG, size); + decode_modrm_reg(u, operand, REGCLASS_DB, size); break; case OP_I3 : operand->type = UD_OP_CONST; @@ -799,18 +878,16 @@ decode_operand(struct ud *u, case OP_ST7: operand->type = UD_OP_REG; operand->base = (type - OP_ST0) + UD_R_ST0; - operand->size = 0; + operand->size = 80; break; - case OP_AX: - operand->type = UD_OP_REG; - operand->base = UD_R_AX; - operand->size = 16; + case OP_L: + decode_vex_immreg(u, operand, size); break; default : operand->type = UD_NONE; break; } - return 0; + return operand->type; } @@ -827,12 +904,21 @@ decode_operands(struct ud* u) decode_operand(u, &u->operand[0], u->itab_entry->operand1.type, u->itab_entry->operand1.size); - decode_operand(u, &u->operand[1], - u->itab_entry->operand2.type, - u->itab_entry->operand2.size); - decode_operand(u, &u->operand[2], - u->itab_entry->operand3.type, - u->itab_entry->operand3.size); + if (u->operand[0].type != UD_NONE) { + decode_operand(u, &u->operand[1], + u->itab_entry->operand2.type, + u->itab_entry->operand2.size); + } + if (u->operand[1].type != UD_NONE) { + decode_operand(u, &u->operand[2], + u->itab_entry->operand3.type, + u->itab_entry->operand3.size); + } + if (u->operand[2].type != UD_NONE) { + decode_operand(u, &u->operand[3], + u->itab_entry->operand4.type, + u->itab_entry->operand4.size); + } return 0; } @@ -852,19 +938,40 @@ clear_insn(register struct ud* u) u->pfx_rep = 0; u->pfx_repe = 0; u->pfx_rex = 0; - u->pfx_insn = 0; + u->pfx_str = 0; u->mnemonic = UD_Inone; u->itab_entry = NULL; u->have_modrm = 0; + u->br_far = 0; + u->vex_op = 0; + u->_rex = 0; + u->operand[0].type = UD_NONE; + u->operand[1].type = UD_NONE; + u->operand[2].type = UD_NONE; + u->operand[3].type = UD_NONE; +} - memset( &u->operand[ 0 ], 0, sizeof( struct ud_operand ) ); - memset( &u->operand[ 1 ], 0, sizeof( struct ud_operand ) ); - memset( &u->operand[ 2 ], 0, sizeof( struct ud_operand ) ); + +static UD_INLINE int +resolve_pfx_str(struct ud* u) +{ + if (u->pfx_str == 0xf3) { + if (P_STR(u->itab_entry->prefix)) { + u->pfx_rep = 0xf3; + } else { + u->pfx_repe = 0xf3; + } + } else if (u->pfx_str == 0xf2) { + u->pfx_repne = 0xf3; + } + return 0; } + static int resolve_mode( struct ud* u ) { + int default64; /* if in error state, bail out */ if ( u->error ) return -1; @@ -873,22 +980,34 @@ resolve_mode( struct ud* u ) /* Check validity of instruction m64 */ if ( P_INV64( u->itab_entry->prefix ) ) { - u->error = 1; - return -1; + UDERR(u, "instruction invalid in 64bits\n"); + return -1; } - /* effective rex prefix is the effective mask for the - * instruction hard-coded in the opcode map. + /* compute effective rex based on, + * - vex prefix (if any) + * - rex prefix (if any, and not vex) + * - allowed prefixes specified by the opcode map */ - u->pfx_rex = ( u->pfx_rex & 0x40 ) | - ( u->pfx_rex & REX_PFX_MASK( u->itab_entry->prefix ) ); + if (u->vex_op == 0xc4) { + /* vex has rex.rxb in 1's complement */ + u->_rex = ((~(u->vex_b1 >> 5) & 0x7) /* rex.0rxb */ | + ((u->vex_b2 >> 4) & 0x8) /* rex.w000 */); + } else if (u->vex_op == 0xc5) { + /* vex has rex.r in 1's complement */ + u->_rex = (~(u->vex_b1 >> 5)) & 4; + } else { + UD_ASSERT(u->vex_op == 0); + u->_rex = u->pfx_rex; + } + u->_rex &= REX_PFX_MASK(u->itab_entry->prefix); /* whether this instruction has a default operand size of * 64bit, also hardcoded into the opcode map. */ - u->default64 = P_DEF64( u->itab_entry->prefix ); + default64 = P_DEF64( u->itab_entry->prefix ); /* calculate effective operand size */ - if ( REX_W( u->pfx_rex ) ) { + if (REX_W(u->_rex)) { u->opr_mode = 64; } else if ( u->pfx_opr ) { u->opr_mode = 16; @@ -897,7 +1016,7 @@ resolve_mode( struct ud* u ) * the effective operand size in the absence of rex.w * prefix is 32. */ - u->opr_mode = ( u->default64 ) ? 64 : 32; + u->opr_mode = default64 ? 64 : 32; } /* calculate effective address size */ @@ -910,45 +1029,18 @@ resolve_mode( struct ud* u ) u->adr_mode = ( u->pfx_adr ) ? 32 : 16; } - /* These flags determine which operand to apply the operand size - * cast to. - */ - u->c1 = ( P_C1( u->itab_entry->prefix ) ) ? 1 : 0; - u->c2 = ( P_C2( u->itab_entry->prefix ) ) ? 1 : 0; - u->c3 = ( P_C3( u->itab_entry->prefix ) ) ? 1 : 0; - - /* set flags for implicit addressing */ - u->implicit_addr = P_IMPADDR( u->itab_entry->prefix ); - - return 0; -} - -static int gen_hex( struct ud *u ) -{ - unsigned int i; - unsigned char *src_ptr = ud_inp_sess( u ); - char* src_hex; - - /* bail out if in error stat. */ - if ( u->error ) return -1; - /* output buffer pointe */ - src_hex = ( char* ) u->insn_hexcode; - /* for each byte used to decode instruction */ - for ( i = 0; i < u->inp_ctr; ++i, ++src_ptr) { - sprintf( src_hex, "%02x", *src_ptr & 0xFF ); - src_hex += 2; - } return 0; } -static inline int +static UD_INLINE int decode_insn(struct ud *u, uint16_t ptr) { - ASSERT((ptr & 0x8000) == 0); + UD_ASSERT((ptr & 0x8000) == 0); u->itab_entry = &ud_itab[ ptr ]; u->mnemonic = u->itab_entry->mnemonic; - return (resolve_mode(u) == 0 && + return (resolve_pfx_str(u) == 0 && + resolve_mode(u) == 0 && decode_operands(u) == 0 && resolve_mnemonic(u) == 0) ? 0 : -1; } @@ -965,19 +1057,19 @@ decode_insn(struct ud *u, uint16_t ptr) * valid entry in the table, decode the operands, and read the final * byte to resolve the menmonic. */ -static inline int +static UD_INLINE int decode_3dnow(struct ud* u) { uint16_t ptr; - ASSERT(u->le->type == UD_TAB__OPC_3DNOW); - ASSERT(u->le->table[0xc] != 0); + UD_ASSERT(u->le->type == UD_TAB__OPC_3DNOW); + UD_ASSERT(u->le->table[0xc] != 0); decode_insn(u, u->le->table[0xc]); - ud_inp_next(u); + inp_next(u); if (u->error) { return -1; } - ptr = u->le->table[ud_inp_curr(u)]; - ASSERT((ptr & 0x8000) == 0); + ptr = u->le->table[inp_curr(u)]; + UD_ASSERT((ptr & 0x8000) == 0); u->mnemonic = ud_itab[ptr].mnemonic; return 0; } @@ -986,7 +1078,18 @@ decode_3dnow(struct ud* u) static int decode_ssepfx(struct ud *u) { - uint8_t idx = ((u->pfx_insn & 0xf) + 1) / 2; + uint8_t idx; + uint8_t pfx; + + /* + * String prefixes (f2, f3) take precedence over operand + * size prefix (66). + */ + pfx = u->pfx_str; + if (pfx == 0) { + pfx = u->pfx_opr; + } + idx = ((pfx & 0xf) + 1) / 2; if (u->le->table[idx] == 0) { idx = 0; } @@ -995,23 +1098,50 @@ decode_ssepfx(struct ud *u) * "Consume" the prefix as a part of the opcode, so it is no * longer exported as an instruction prefix. */ - switch (u->pfx_insn) { - case 0xf2: - u->pfx_repne = 0; - break; - case 0xf3: - u->pfx_rep = 0; - u->pfx_repe = 0; - break; - case 0x66: + u->pfx_str = 0; + if (pfx == 0x66) { + /* + * consume "66" only if it was used for decoding, leaving + * it to be used as an operands size override for some + * simd instructions. + */ u->pfx_opr = 0; - break; } } return decode_ext(u, u->le->table[idx]); } +static int +decode_vex(struct ud *u) +{ + uint8_t index; + if (u->dis_mode != 64 && MODRM_MOD(inp_peek(u)) != 0x3) { + index = 0; + } else { + u->vex_op = inp_curr(u); + u->vex_b1 = inp_next(u); + if (u->vex_op == 0xc4) { + uint8_t pp, m; + /* 3-byte vex */ + u->vex_b2 = inp_next(u); + UD_RETURN_ON_ERROR(u); + m = u->vex_b1 & 0x1f; + if (m == 0 || m > 3) { + UD_RETURN_WITH_ERROR(u, "reserved vex.m-mmmm value"); + } + pp = u->vex_b2 & 0x3; + index = (pp << 2) | m; + } else { + /* 2-byte vex */ + UD_ASSERT(u->vex_op == 0xc5); + index = 0x1 | ((u->vex_b1 & 0x3) << 2); + } + } + return decode_ext(u, u->le->table[index]); +} + + /* * decode_ext() * @@ -1038,7 +1168,7 @@ decode_ext(struct ud *u, uint16_t ptr) * 16 = 0,, 32 = 1, 64 = 2 */ case UD_TAB__OPC_MODE: - idx = u->dis_mode / 32; + idx = u->dis_mode != 64 ? 0 : 1; break; case UD_TAB__OPC_OSIZE: idx = eff_opr_mode(u->dis_mode, REX_W(u->pfx_rex), u->pfx_opr) / 32; @@ -1067,8 +1197,19 @@ decode_ext(struct ud *u, uint16_t ptr) break; case UD_TAB__OPC_SSE: return decode_ssepfx(u); + case UD_TAB__OPC_VEX: + return decode_vex(u); + case UD_TAB__OPC_VEX_W: + idx = vex_w(u); + break; + case UD_TAB__OPC_VEX_L: + idx = vex_l(u); + break; + case UD_TAB__OPC_TABLE: + inp_next(u); + return decode_opcode(u); default: - ASSERT(!"not reached"); + UD_ASSERT(!"not reached"); break; } @@ -1076,22 +1217,13 @@ decode_ext(struct ud *u, uint16_t ptr) } -static inline int +static int decode_opcode(struct ud *u) { uint16_t ptr; - ASSERT(u->le->type == UD_TAB__OPC_TABLE); - ud_inp_next(u); - if (u->error) { - return -1; - } - ptr = u->le->table[ud_inp_curr(u)]; - if (ptr & 0x8000) { - u->le = &ud_lookup_table_list[ptr & ~0x8000]; - if (u->le->type == UD_TAB__OPC_TABLE) { - return decode_opcode(u); - } - } + UD_ASSERT(u->le->type == UD_TAB__OPC_TABLE); + UD_RETURN_ON_ERROR(u); + ptr = u->le->table[inp_curr(u)]; return decode_ext(u, ptr); } @@ -1103,7 +1235,7 @@ decode_opcode(struct ud *u) unsigned int ud_decode(struct ud *u) { - ud_inp_start(u); + inp_start(u); clear_insn(u); u->le = &ud_lookup_table_list[0]; u->error = decode_prefixes(u) == -1 || @@ -1114,7 +1246,7 @@ ud_decode(struct ud *u) /* clear out the decode data. */ clear_insn(u); /* mark the sequence of bytes as invalid. */ - u->itab_entry = & s_ie__invalid; + u->itab_entry = &ud_itab[0]; /* entry 0 is invalid */ u->mnemonic = u->itab_entry->mnemonic; } @@ -1127,16 +1259,15 @@ ud_decode(struct ud *u) u->pfx_seg = 0; u->insn_offset = u->pc; /* set offset of instruction */ - u->insn_fill = 0; /* set translation buffer index to 0 */ + u->asm_buf_fill = 0; /* set translation buffer index to 0 */ u->pc += u->inp_ctr; /* move program counter by bytes decoded */ - gen_hex( u ); /* generate hex code */ /* return number of bytes disassembled. */ return u->inp_ctr; } +#endif // USE(UDIS86) + /* vim: set ts=2 sw=2 expandtab */ - -#endif // USE(UDIS86) diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_decode.h b/Source/JavaScriptCore/disassembler/udis86/udis86_decode.h index 940ed5ad6..411c8830e 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_decode.h +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_decode.h @@ -27,74 +27,45 @@ #define UD_DECODE_H #include "udis86_types.h" +#include "udis86_udint.h" #include "udis86_itab.h" #define MAX_INSN_LENGTH 15 -/* register classes */ -#define T_NONE 0 -#define T_GPR 1 -#define T_MMX 2 -#define T_CRG 3 -#define T_DBG 4 -#define T_SEG 5 -#define T_XMM 6 - /* itab prefix bits */ #define P_none ( 0 ) -#define P_cast ( 1 << 0 ) -#define P_CAST(n) ( ( n >> 0 ) & 1 ) -#define P_c1 ( 1 << 0 ) -#define P_C1(n) ( ( n >> 0 ) & 1 ) -#define P_rexb ( 1 << 1 ) -#define P_REXB(n) ( ( n >> 1 ) & 1 ) -#define P_depM ( 1 << 2 ) -#define P_DEPM(n) ( ( n >> 2 ) & 1 ) -#define P_c3 ( 1 << 3 ) -#define P_C3(n) ( ( n >> 3 ) & 1 ) -#define P_inv64 ( 1 << 4 ) -#define P_INV64(n) ( ( n >> 4 ) & 1 ) + +#define P_inv64 ( 1 << 0 ) +#define P_INV64(n) ( ( n >> 0 ) & 1 ) +#define P_def64 ( 1 << 1 ) +#define P_DEF64(n) ( ( n >> 1 ) & 1 ) + +#define P_oso ( 1 << 2 ) +#define P_OSO(n) ( ( n >> 2 ) & 1 ) +#define P_aso ( 1 << 3 ) +#define P_ASO(n) ( ( n >> 3 ) & 1 ) + +#define P_rexb ( 1 << 4 ) +#define P_REXB(n) ( ( n >> 4 ) & 1 ) #define P_rexw ( 1 << 5 ) #define P_REXW(n) ( ( n >> 5 ) & 1 ) -#define P_c2 ( 1 << 6 ) -#define P_C2(n) ( ( n >> 6 ) & 1 ) -#define P_def64 ( 1 << 7 ) -#define P_DEF64(n) ( ( n >> 7 ) & 1 ) -#define P_rexr ( 1 << 8 ) -#define P_REXR(n) ( ( n >> 8 ) & 1 ) -#define P_oso ( 1 << 9 ) -#define P_OSO(n) ( ( n >> 9 ) & 1 ) -#define P_aso ( 1 << 10 ) -#define P_ASO(n) ( ( n >> 10 ) & 1 ) -#define P_rexx ( 1 << 11 ) -#define P_REXX(n) ( ( n >> 11 ) & 1 ) -#define P_ImpAddr ( 1 << 12 ) -#define P_IMPADDR(n) ( ( n >> 12 ) & 1 ) -#define P_seg ( 1 << 13 ) -#define P_SEG(n) ( ( n >> 13 ) & 1 ) -#define P_sext ( 1 << 14 ) -#define P_SEXT(n) ( ( n >> 14 ) & 1 ) - -/* rex prefix bits */ -#define REX_W(r) ( ( 0xF & ( r ) ) >> 3 ) -#define REX_R(r) ( ( 0x7 & ( r ) ) >> 2 ) -#define REX_X(r) ( ( 0x3 & ( r ) ) >> 1 ) -#define REX_B(r) ( ( 0x1 & ( r ) ) >> 0 ) -#define REX_PFX_MASK(n) ( ( P_REXW(n) << 3 ) | \ - ( P_REXR(n) << 2 ) | \ - ( P_REXX(n) << 1 ) | \ - ( P_REXB(n) << 0 ) ) - -/* scable-index-base bits */ -#define SIB_S(b) ( ( b ) >> 6 ) -#define SIB_I(b) ( ( ( b ) >> 3 ) & 7 ) -#define SIB_B(b) ( ( b ) & 7 ) - -/* modrm bits */ -#define MODRM_REG(b) ( ( ( b ) >> 3 ) & 7 ) -#define MODRM_NNN(b) ( ( ( b ) >> 3 ) & 7 ) -#define MODRM_MOD(b) ( ( ( b ) >> 6 ) & 3 ) -#define MODRM_RM(b) ( ( b ) & 7 ) +#define P_rexr ( 1 << 6 ) +#define P_REXR(n) ( ( n >> 6 ) & 1 ) +#define P_rexx ( 1 << 7 ) +#define P_REXX(n) ( ( n >> 7 ) & 1 ) + +#define P_seg ( 1 << 8 ) +#define P_SEG(n) ( ( n >> 8 ) & 1 ) + +#define P_vexl ( 1 << 9 ) +#define P_VEXL(n) ( ( n >> 9 ) & 1 ) +#define P_vexw ( 1 << 10 ) +#define P_VEXW(n) ( ( n >> 10 ) & 1 ) + +#define P_str ( 1 << 11 ) +#define P_STR(n) ( ( n >> 11 ) & 1 ) +#define P_strz ( 1 << 12 ) +#define P_STR_ZF(n) ( ( n >> 12 ) & 1 ) /* operand type constants -- order is important! */ @@ -102,25 +73,15 @@ enum ud_operand_code { OP_NONE, OP_A, OP_E, OP_M, OP_G, - OP_I, - - OP_AL, OP_CL, OP_DL, OP_BL, - OP_AH, OP_CH, OP_DH, OP_BH, - - OP_ALr8b, OP_CLr9b, OP_DLr10b, OP_BLr11b, - OP_AHr12b, OP_CHr13b, OP_DHr14b, OP_BHr15b, - - OP_AX, OP_CX, OP_DX, OP_BX, - OP_SI, OP_DI, OP_SP, OP_BP, - - OP_rAX, OP_rCX, OP_rDX, OP_rBX, - OP_rSP, OP_rBP, OP_rSI, OP_rDI, + OP_I, OP_F, - OP_rAXr8, OP_rCXr9, OP_rDXr10, OP_rBXr11, - OP_rSPr12, OP_rBPr13, OP_rSIr14, OP_rDIr15, + OP_R0, OP_R1, OP_R2, OP_R3, + OP_R4, OP_R5, OP_R6, OP_R7, - OP_eAX, OP_eCX, OP_eDX, OP_eBX, - OP_eSP, OP_eBP, OP_eSI, OP_eDI, + OP_AL, OP_CL, OP_DL, + OP_AX, OP_CX, OP_DX, + OP_eAX, OP_eCX, OP_eDX, + OP_rAX, OP_rCX, OP_rDX, OP_ES, OP_CS, OP_SS, OP_DS, OP_FS, OP_GS, @@ -129,45 +90,71 @@ enum ud_operand_code { OP_ST4, OP_ST5, OP_ST6, OP_ST7, OP_J, OP_S, OP_O, - OP_I1, OP_I3, + OP_I1, OP_I3, OP_sI, OP_V, OP_W, OP_Q, OP_P, + OP_U, OP_N, OP_MU, OP_H, + OP_L, - OP_R, OP_C, OP_D, OP_VR, OP_PR, + OP_R, OP_C, OP_D, OP_MR } UD_ATTR_PACKED; -/* operand size constants */ - -enum ud_operand_size { - SZ_NA = 0, - SZ_Z = 1, - SZ_V = 2, - SZ_P = 3, - SZ_WP = 4, - SZ_DP = 5, - SZ_MDQ = 6, - SZ_RDQ = 7, - - /* the following values are used as is, - * and thus hard-coded. changing them - * will break internals - */ - SZ_B = 8, - SZ_W = 16, - SZ_D = 32, - SZ_Q = 64, - SZ_T = 80, - SZ_O = 128, - - SZ_WV = 17, - SZ_BV = 18, - SZ_DY = 19 - -} UD_ATTR_PACKED; +/* + * Operand size constants + * + * Symbolic constants for various operand sizes. Some of these constants + * are given a value equal to the width of the data (SZ_B == 8), such + * that they maybe used interchangeably in the internals. Modifying them + * will most certainly break things! + */ +typedef uint16_t ud_operand_size_t; + +#define SZ_NA 0 +#define SZ_Z 1 +#define SZ_V 2 +#define SZ_Y 3 +#define SZ_X 4 +#define SZ_RDQ 7 +#define SZ_B 8 +#define SZ_W 16 +#define SZ_D 32 +#define SZ_Q 64 +#define SZ_T 80 +#define SZ_O 12 +#define SZ_DQ 128 /* double quad */ +#define SZ_QQ 256 /* quad quad */ + +/* + * Complex size types; that encode sizes for operands of type MR (memory or + * register); for internal use only. Id space above 256. + */ +#define SZ_BD ((SZ_B << 8) | SZ_D) +#define SZ_BV ((SZ_B << 8) | SZ_V) +#define SZ_WD ((SZ_W << 8) | SZ_D) +#define SZ_WV ((SZ_W << 8) | SZ_V) +#define SZ_WY ((SZ_W << 8) | SZ_Y) +#define SZ_DY ((SZ_D << 8) | SZ_Y) +#define SZ_WO ((SZ_W << 8) | SZ_O) +#define SZ_DO ((SZ_D << 8) | SZ_O) +#define SZ_QO ((SZ_Q << 8) | SZ_O) + + +/* resolve complex size type. + */ +static UD_INLINE ud_operand_size_t +Mx_mem_size(ud_operand_size_t size) +{ + return (size >> 8) & 0xff; +} +static UD_INLINE ud_operand_size_t +Mx_reg_size(ud_operand_size_t size) +{ + return size & 0xff; +} /* A single operand of an entry in the instruction table. * (internal use only) @@ -175,7 +162,7 @@ enum ud_operand_size { struct ud_itab_entry_operand { enum ud_operand_code type; - enum ud_operand_size size; + ud_operand_size_t size; }; @@ -188,6 +175,7 @@ struct ud_itab_entry struct ud_itab_entry_operand operand1; struct ud_itab_entry_operand operand2; struct ud_itab_entry_operand operand3; + struct ud_itab_entry_operand operand4; uint32_t prefix; }; @@ -197,55 +185,6 @@ struct ud_lookup_table_list_entry { const char *meta; }; - -static inline unsigned int sse_pfx_idx( const unsigned int pfx ) -{ - /* 00 = 0 - * f2 = 1 - * f3 = 2 - * 66 = 3 - */ - return ( ( pfx & 0xf ) + 1 ) / 2; -} - -static inline unsigned int mode_idx( const unsigned int mode ) -{ - /* 16 = 0 - * 32 = 1 - * 64 = 2 - */ - return ( mode / 32 ); -} - -static inline unsigned int modrm_mod_idx( const unsigned int mod ) -{ - /* !11 = 0 - * 11 = 1 - */ - return ( mod + 1 ) / 4; -} - -static inline unsigned int vendor_idx( const unsigned int vendor ) -{ - switch ( vendor ) { - case UD_VENDOR_AMD: return 0; - case UD_VENDOR_INTEL: return 1; - case UD_VENDOR_ANY: return 2; - default: return 2; - } -} - -static inline unsigned int is_group_ptr( uint16_t ptr ) -{ - return ( 0x8000 & ptr ); -} - -static inline unsigned int group_idx( uint16_t ptr ) -{ - return ( ~0x8000 & ptr ); -} - - extern struct ud_itab_entry ud_itab[]; extern struct ud_lookup_table_list_entry ud_lookup_table_list[]; diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_extern.h b/Source/JavaScriptCore/disassembler/udis86/udis86_extern.h index 8e87721e8..bf3314d09 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_extern.h +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_extern.h @@ -1,6 +1,6 @@ /* udis86 - libudis86/extern.h * - * Copyright (c) 2002-2009 Vivek Thampi + * Copyright (c) 2002-2009, 2013 Vivek Thampi * All rights reserved. * * Redistribution and use in source and binary forms, with or without modification, @@ -32,57 +32,82 @@ extern "C" { #include "udis86_types.h" +#if defined(_MSC_VER) && defined(_USRDLL) +# ifdef LIBUDIS86_EXPORTS +# define LIBUDIS86_DLLEXTERN __declspec(dllexport) +# else +# define LIBUDIS86_DLLEXTERN __declspec(dllimport) +# endif +#else +# define LIBUDIS86_DLLEXTERN +#endif + /* ============================= PUBLIC API ================================= */ -extern void ud_init(struct ud*); +extern LIBUDIS86_DLLEXTERN void ud_init(struct ud*); -extern void ud_set_mode(struct ud*, uint8_t); +extern LIBUDIS86_DLLEXTERN void ud_set_mode(struct ud*, uint8_t); -extern void ud_set_pc(struct ud*, uint64_t); +extern LIBUDIS86_DLLEXTERN void ud_set_pc(struct ud*, uint64_t); -extern void ud_set_input_hook(struct ud*, int (*)(struct ud*)); +extern LIBUDIS86_DLLEXTERN void ud_set_input_hook(struct ud*, int (*)(struct ud*)); -extern void ud_set_input_buffer(struct ud*, uint8_t*, size_t); +extern LIBUDIS86_DLLEXTERN void ud_set_input_buffer(struct ud*, const uint8_t*, size_t); #ifndef __UD_STANDALONE__ -extern void ud_set_input_file(struct ud*, FILE*); +extern LIBUDIS86_DLLEXTERN void ud_set_input_file(struct ud*, FILE*); #endif /* __UD_STANDALONE__ */ -extern void ud_set_vendor(struct ud*, unsigned); +extern LIBUDIS86_DLLEXTERN void ud_set_vendor(struct ud*, unsigned); + +extern LIBUDIS86_DLLEXTERN void ud_set_syntax(struct ud*, void (*)(struct ud*)); + +extern LIBUDIS86_DLLEXTERN void ud_input_skip(struct ud*, size_t); + +extern LIBUDIS86_DLLEXTERN int ud_input_end(const struct ud*); -extern void ud_set_syntax(struct ud*, void (*)(struct ud*)); +extern LIBUDIS86_DLLEXTERN unsigned int ud_decode(struct ud*); -extern void ud_input_skip(struct ud*, size_t); +extern LIBUDIS86_DLLEXTERN unsigned int ud_disassemble(struct ud*); -extern int ud_input_end(struct ud*); +extern LIBUDIS86_DLLEXTERN void ud_translate_intel(struct ud*); -extern unsigned int ud_decode(struct ud*); +extern LIBUDIS86_DLLEXTERN void ud_translate_att(struct ud*); -extern unsigned int ud_disassemble(struct ud*); +extern LIBUDIS86_DLLEXTERN const char* ud_insn_asm(const struct ud* u); -extern void ud_translate_intel(struct ud*); +extern LIBUDIS86_DLLEXTERN const uint8_t* ud_insn_ptr(const struct ud* u); -extern void ud_translate_att(struct ud*); +extern LIBUDIS86_DLLEXTERN uint64_t ud_insn_off(const struct ud*); -extern char* ud_insn_asm(struct ud* u); +extern LIBUDIS86_DLLEXTERN const char* ud_insn_hex(struct ud*); -extern uint8_t* ud_insn_ptr(struct ud* u); +extern LIBUDIS86_DLLEXTERN unsigned int ud_insn_len(const struct ud* u); -extern uint64_t ud_insn_off(struct ud*); +extern LIBUDIS86_DLLEXTERN const struct ud_operand* ud_insn_opr(const struct ud *u, unsigned int n); -extern char* ud_insn_hex(struct ud*); +extern LIBUDIS86_DLLEXTERN int ud_opr_is_sreg(const struct ud_operand *opr); -extern unsigned int ud_insn_len(struct ud* u); +extern LIBUDIS86_DLLEXTERN int ud_opr_is_gpr(const struct ud_operand *opr); -extern const char* ud_lookup_mnemonic(enum ud_mnemonic_code c); +extern LIBUDIS86_DLLEXTERN enum ud_mnemonic_code ud_insn_mnemonic(const struct ud *u); -extern void ud_set_user_opaque_data(struct ud*, void*); +extern LIBUDIS86_DLLEXTERN const char* ud_lookup_mnemonic(enum ud_mnemonic_code c); -extern void *ud_get_user_opaque_data(struct ud*); +extern LIBUDIS86_DLLEXTERN void ud_set_user_opaque_data(struct ud*, void*); + +extern LIBUDIS86_DLLEXTERN void* ud_get_user_opaque_data(const struct ud*); + +extern LIBUDIS86_DLLEXTERN void ud_set_asm_buffer(struct ud *u, char *buf, size_t size); + +extern LIBUDIS86_DLLEXTERN void ud_set_sym_resolver(struct ud *u, + const char* (*resolver)(struct ud*, + uint64_t addr, + int64_t *offset)); /* ========================================================================== */ #ifdef __cplusplus } #endif -#endif +#endif /* UD_EXTERN_H */ diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_input.c b/Source/JavaScriptCore/disassembler/udis86/udis86_input.c deleted file mode 100644 index 4dbe32876..000000000 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_input.c +++ /dev/null @@ -1,262 +0,0 @@ -/* udis86 - libudis86/input.c - * - * Copyright (c) 2002-2009 Vivek Thampi - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without modification, - * are permitted provided that the following conditions are met: - * - * * Redistributions of source code must retain the above copyright notice, - * this list of conditions and the following disclaimer. - * * Redistributions in binary form must reproduce the above copyright notice, - * this list of conditions and the following disclaimer in the documentation - * and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR - * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON - * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ -#include "config.h" - -#if USE(UDIS86) - -#include "udis86_extern.h" -#include "udis86_types.h" -#include "udis86_input.h" - -/* ----------------------------------------------------------------------------- - * inp_buff_hook() - Hook for buffered inputs. - * ----------------------------------------------------------------------------- - */ -static int -inp_buff_hook(struct ud* u) -{ - if (u->inp_buff < u->inp_buff_end) - return *u->inp_buff++; - else return -1; -} - -#ifndef __UD_STANDALONE__ -/* ----------------------------------------------------------------------------- - * inp_file_hook() - Hook for FILE inputs. - * ----------------------------------------------------------------------------- - */ -static int -inp_file_hook(struct ud* u) -{ - return fgetc(u->inp_file); -} -#endif /* __UD_STANDALONE__*/ - -/* ============================================================================= - * ud_inp_set_hook() - Sets input hook. - * ============================================================================= - */ -extern void -ud_set_input_hook(register struct ud* u, int (*hook)(struct ud*)) -{ - u->inp_hook = hook; - ud_inp_init(u); -} - -extern void -ud_set_user_opaque_data( struct ud * u, void * opaque ) -{ - u->user_opaque_data = opaque; -} - -extern void * -ud_get_user_opaque_data( struct ud * u ) -{ - return u->user_opaque_data; -} - -/* ============================================================================= - * ud_inp_set_buffer() - Set buffer as input. - * ============================================================================= - */ -extern void -ud_set_input_buffer(register struct ud* u, uint8_t* buf, size_t len) -{ - u->inp_hook = inp_buff_hook; - u->inp_buff = buf; - u->inp_buff_end = buf + len; - ud_inp_init(u); -} - -#ifndef __UD_STANDALONE__ -/* ============================================================================= - * ud_input_set_file() - Set buffer as input. - * ============================================================================= - */ -extern void -ud_set_input_file(register struct ud* u, FILE* f) -{ - u->inp_hook = inp_file_hook; - u->inp_file = f; - ud_inp_init(u); -} -#endif /* __UD_STANDALONE__ */ - -/* ============================================================================= - * ud_input_skip() - Skip n input bytes. - * ============================================================================= - */ -extern void -ud_input_skip(struct ud* u, size_t n) -{ - while (n--) { - u->inp_hook(u); - } -} - -/* ============================================================================= - * ud_input_end() - Test for end of input. - * ============================================================================= - */ -extern int -ud_input_end(struct ud* u) -{ - return (u->inp_curr == u->inp_fill) && u->inp_end; -} - -/* ----------------------------------------------------------------------------- - * ud_inp_next() - Loads and returns the next byte from input. - * - * inp_curr and inp_fill are pointers to the cache. The program is written based - * on the property that they are 8-bits in size, and will eventually wrap around - * forming a circular buffer. So, the size of the cache is 256 in size, kind of - * unnecessary yet optimized. - * - * A buffer inp_sess stores the bytes disassembled for a single session. - * ----------------------------------------------------------------------------- - */ -extern uint8_t ud_inp_next(struct ud* u) -{ - int c = -1; - /* if current pointer is not upto the fill point in the - * input cache. - */ - if ( u->inp_curr != u->inp_fill ) { - c = u->inp_cache[ ++u->inp_curr ]; - /* if !end-of-input, call the input hook and get a byte */ - } else if ( u->inp_end || ( c = u->inp_hook( u ) ) == -1 ) { - /* end-of-input, mark it as an error, since the decoder, - * expected a byte more. - */ - u->error = 1; - /* flag end of input */ - u->inp_end = 1; - return 0; - } else { - /* increment pointers, we have a new byte. */ - u->inp_curr = ++u->inp_fill; - /* add the byte to the cache */ - u->inp_cache[ u->inp_fill ] = c; - } - /* record bytes input per decode-session. */ - u->inp_sess[ u->inp_ctr++ ] = c; - /* return byte */ - return ( uint8_t ) c; -} - -/* ----------------------------------------------------------------------------- - * ud_inp_back() - Move back a single byte in the stream. - * ----------------------------------------------------------------------------- - */ -extern void -ud_inp_back(struct ud* u) -{ - if ( u->inp_ctr > 0 ) { - --u->inp_curr; - --u->inp_ctr; - } -} - -/* ----------------------------------------------------------------------------- - * ud_inp_peek() - Peek into the next byte in source. - * ----------------------------------------------------------------------------- - */ -extern uint8_t -ud_inp_peek(struct ud* u) -{ - uint8_t r = ud_inp_next(u); - if ( !u->error ) ud_inp_back(u); /* Don't backup if there was an error */ - return r; -} - -/* ----------------------------------------------------------------------------- - * ud_inp_move() - Move ahead n input bytes. - * ----------------------------------------------------------------------------- - */ -extern void -ud_inp_move(struct ud* u, size_t n) -{ - while (n--) - ud_inp_next(u); -} - -/*------------------------------------------------------------------------------ - * ud_inp_uintN() - return uintN from source. - *------------------------------------------------------------------------------ - */ -extern uint8_t -ud_inp_uint8(struct ud* u) -{ - return ud_inp_next(u); -} - -extern uint16_t -ud_inp_uint16(struct ud* u) -{ - uint16_t r, ret; - - ret = ud_inp_next(u); - r = ud_inp_next(u); - return ret | (r << 8); -} - -extern uint32_t -ud_inp_uint32(struct ud* u) -{ - uint32_t r, ret; - - ret = ud_inp_next(u); - r = ud_inp_next(u); - ret = ret | (r << 8); - r = ud_inp_next(u); - ret = ret | (r << 16); - r = ud_inp_next(u); - return ret | (r << 24); -} - -extern uint64_t -ud_inp_uint64(struct ud* u) -{ - uint64_t r, ret; - - ret = ud_inp_next(u); - r = ud_inp_next(u); - ret = ret | (r << 8); - r = ud_inp_next(u); - ret = ret | (r << 16); - r = ud_inp_next(u); - ret = ret | (r << 24); - r = ud_inp_next(u); - ret = ret | (r << 32); - r = ud_inp_next(u); - ret = ret | (r << 40); - r = ud_inp_next(u); - ret = ret | (r << 48); - r = ud_inp_next(u); - return ret | (r << 56); -} - -#endif // USE(UDIS86) diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_input.h b/Source/JavaScriptCore/disassembler/udis86/udis86_input.h deleted file mode 100644 index 96865a88b..000000000 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_input.h +++ /dev/null @@ -1,67 +0,0 @@ -/* udis86 - libudis86/input.h - * - * Copyright (c) 2002-2009 Vivek Thampi - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without modification, - * are permitted provided that the following conditions are met: - * - * * Redistributions of source code must retain the above copyright notice, - * this list of conditions and the following disclaimer. - * * Redistributions in binary form must reproduce the above copyright notice, - * this list of conditions and the following disclaimer in the documentation - * and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR - * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON - * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ -#ifndef UD_INPUT_H -#define UD_INPUT_H - -#include "udis86_types.h" - -uint8_t ud_inp_next(struct ud*); -uint8_t ud_inp_peek(struct ud*); -uint8_t ud_inp_uint8(struct ud*); -uint16_t ud_inp_uint16(struct ud*); -uint32_t ud_inp_uint32(struct ud*); -uint64_t ud_inp_uint64(struct ud*); -void ud_inp_move(struct ud*, size_t); -void ud_inp_back(struct ud*); - -/* ud_inp_init() - Initializes the input system. */ -#define ud_inp_init(u) \ -do { \ - u->inp_curr = 0; \ - u->inp_fill = 0; \ - u->inp_ctr = 0; \ - u->inp_end = 0; \ -} while (0) - -/* ud_inp_start() - Should be called before each de-code operation. */ -#define ud_inp_start(u) u->inp_ctr = 0 - -/* ud_inp_back() - Resets the current pointer to its position before the current - * instruction disassembly was started. - */ -#define ud_inp_reset(u) \ -do { \ - u->inp_curr -= u->inp_ctr; \ - u->inp_ctr = 0; \ -} while (0) - -/* ud_inp_sess() - Returns the pointer to current session. */ -#define ud_inp_sess(u) (u->inp_sess) - -/* inp_cur() - Returns the current input byte. */ -#define ud_inp_curr(u) ((u)->inp_cache[(u)->inp_curr]) - -#endif diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_syn-att.c b/Source/JavaScriptCore/disassembler/udis86/udis86_syn-att.c index c9c84880a..7d5646e4a 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_syn-att.c +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_syn-att.c @@ -23,6 +23,7 @@ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ + #include "config.h" #if USE(UDIS86) @@ -32,6 +33,7 @@ #include "udis86_decode.h" #include "udis86_itab.h" #include "udis86_syn.h" +#include "udis86_udint.h" /* ----------------------------------------------------------------------------- * opr_cast() - Prints an operand cast. @@ -41,9 +43,9 @@ static void opr_cast(struct ud* u, struct ud_operand* op) { switch(op->size) { - case 16 : case 32 : - mkasm(u, "*"); break; - default: break; + case 16 : case 32 : + ud_asmprintf(u, "*"); break; + default: break; } } @@ -55,107 +57,66 @@ static void gen_operand(struct ud* u, struct ud_operand* op) { switch(op->type) { - case UD_OP_REG: - mkasm(u, "%%%s", ud_reg_tab[op->base - UD_R_AL]); - break; - - case UD_OP_MEM: - if (u->br_far) opr_cast(u, op); - if (u->pfx_seg) - mkasm(u, "%%%s:", ud_reg_tab[u->pfx_seg - UD_R_AL]); - if (op->offset == 8) { - if (op->lval.sbyte < 0) - mkasm(u, "-0x%x", (-op->lval.sbyte) & 0xff); - else - mkasm(u, "0x%x", op->lval.sbyte); - } - else if (op->offset == 16) { - if (op->lval.sword < 0) - mkasm(u, "-0x%x", (-op->lval.sword) & 0xffff); - else - mkasm(u, "0x%x", op->lval.sword); - } else if (op->offset == 32) { - if (op->lval.sdword < 0) - mkasm(u, "-0x%x", (-op->lval.sdword) & 0xffffffff); - else - mkasm(u, "0x%x", op->lval.sdword); - } else if (op->offset == 64) { - if (op->lval.sdword < 0) - mkasm(u, "-0x" FMT64 "x", (uint64_t)-op->lval.sqword); - else - mkasm(u, "0x" FMT64 "x", (uint64_t)op->lval.sqword); - } + case UD_OP_CONST: + ud_asmprintf(u, "$0x%x", op->lval.udword); + break; - if (op->base) - mkasm(u, "(%%%s", ud_reg_tab[op->base - UD_R_AL]); - if (op->index) { - if (op->base) - mkasm(u, ","); - else mkasm(u, "("); - mkasm(u, "%%%s", ud_reg_tab[op->index - UD_R_AL]); - } - if (op->scale) - mkasm(u, ",%d", op->scale); - if (op->base || op->index) - mkasm(u, ")"); - break; + case UD_OP_REG: + ud_asmprintf(u, "%%%s", ud_reg_tab[op->base - UD_R_AL]); + break; - case UD_OP_IMM: { - int64_t imm = 0; - uint64_t sext_mask = 0xffffffffffffffffull; - unsigned sext_size = op->size; - - switch (op->size) { - case 8: imm = op->lval.sbyte; break; - case 16: imm = op->lval.sword; break; - case 32: imm = op->lval.sdword; break; - case 64: imm = op->lval.sqword; break; - } - if ( P_SEXT( u->itab_entry->prefix ) ) { - sext_size = u->operand[ 0 ].size; - if ( u->mnemonic == UD_Ipush ) - /* push sign-extends to operand size */ - sext_size = u->opr_mode; - } - if ( sext_size < 64 ) - sext_mask = ( 1ull << sext_size ) - 1; - mkasm( u, "$0x" FMT64 "x", (uint64_t)(imm & sext_mask) ); - - break; + case UD_OP_MEM: + if (u->br_far) { + opr_cast(u, op); } - - case UD_OP_JIMM: - switch (op->size) { - case 8: - mkasm(u, "0x" FMT64 "x", (uint64_t)(u->pc + op->lval.sbyte)); - break; - case 16: - mkasm(u, "0x" FMT64 "x", (uint64_t)((u->pc + op->lval.sword) & 0xffff) ); - break; - case 32: - if (u->dis_mode == 32) - mkasm(u, "0x" FMT64 "x", (uint64_t)((u->pc + op->lval.sdword) & 0xffffffff)); - else - mkasm(u, "0x" FMT64 "x", (uint64_t)(u->pc + op->lval.sdword)); - break; - default:break; - } - break; - - case UD_OP_PTR: - switch (op->size) { - case 32: - mkasm(u, "$0x%x, $0x%x", op->lval.ptr.seg, - op->lval.ptr.off & 0xFFFF); - break; - case 48: - mkasm(u, "$0x%x, $0x%lx", op->lval.ptr.seg, - (unsigned long)op->lval.ptr.off); - break; - } - break; - - default: return; + if (u->pfx_seg) { + ud_asmprintf(u, "%%%s:", ud_reg_tab[u->pfx_seg - UD_R_AL]); + } + if (op->offset != 0) { + ud_syn_print_mem_disp(u, op, 0); + } + if (op->base) { + ud_asmprintf(u, "(%%%s", ud_reg_tab[op->base - UD_R_AL]); + } + if (op->index) { + if (op->base) { + ud_asmprintf(u, ","); + } else { + ud_asmprintf(u, "("); + } + ud_asmprintf(u, "%%%s", ud_reg_tab[op->index - UD_R_AL]); + } + if (op->scale) { + ud_asmprintf(u, ",%d", op->scale); + } + if (op->base || op->index) { + ud_asmprintf(u, ")"); + } + break; + + case UD_OP_IMM: + ud_asmprintf(u, "$"); + ud_syn_print_imm(u, op); + break; + + case UD_OP_JIMM: + ud_syn_print_addr(u, ud_syn_rel_target(u, op)); + break; + + case UD_OP_PTR: + switch (op->size) { + case 32: + ud_asmprintf(u, "$0x%x, $0x%x", op->lval.ptr.seg, + op->lval.ptr.off & 0xFFFF); + break; + case 48: + ud_asmprintf(u, "$0x%x, $0x%x", op->lval.ptr.seg, + op->lval.ptr.off); + break; + } + break; + + default: return; } } @@ -167,99 +128,108 @@ extern void ud_translate_att(struct ud *u) { int size = 0; - unsigned i; + int star = 0; /* check if P_OSO prefix is used */ if (! P_OSO(u->itab_entry->prefix) && u->pfx_opr) { - switch (u->dis_mode) { - case 16: - mkasm(u, "o32 "); - break; - case 32: - case 64: - mkasm(u, "o16 "); - break; - } + switch (u->dis_mode) { + case 16: + ud_asmprintf(u, "o32 "); + break; + case 32: + case 64: + ud_asmprintf(u, "o16 "); + break; + } } /* check if P_ASO prefix was used */ if (! P_ASO(u->itab_entry->prefix) && u->pfx_adr) { - switch (u->dis_mode) { - case 16: - mkasm(u, "a32 "); - break; - case 32: - mkasm(u, "a16 "); - break; - case 64: - mkasm(u, "a32 "); - break; - } + switch (u->dis_mode) { + case 16: + ud_asmprintf(u, "a32 "); + break; + case 32: + ud_asmprintf(u, "a16 "); + break; + case 64: + ud_asmprintf(u, "a32 "); + break; + } } if (u->pfx_lock) - mkasm(u, "lock "); - if (u->pfx_rep) - mkasm(u, "rep "); - if (u->pfx_repne) - mkasm(u, "repne "); + ud_asmprintf(u, "lock "); + if (u->pfx_rep) { + ud_asmprintf(u, "rep "); + } else if (u->pfx_repe) { + ud_asmprintf(u, "repe "); + } else if (u->pfx_repne) { + ud_asmprintf(u, "repne "); + } /* special instructions */ switch (u->mnemonic) { - case UD_Iretf: - mkasm(u, "lret "); - break; - case UD_Idb: - mkasm(u, ".byte 0x%x", u->operand[0].lval.ubyte); - return; - case UD_Ijmp: - case UD_Icall: - if (u->br_far) mkasm(u, "l"); - mkasm(u, "%s", ud_lookup_mnemonic(u->mnemonic)); - break; - case UD_Ibound: - case UD_Ienter: - if (u->operand[0].type != UD_NONE) - gen_operand(u, &u->operand[0]); - if (u->operand[1].type != UD_NONE) { - mkasm(u, ","); - gen_operand(u, &u->operand[1]); - } - return; - default: - mkasm(u, "%s", ud_lookup_mnemonic(u->mnemonic)); + case UD_Iretf: + ud_asmprintf(u, "lret "); + break; + case UD_Idb: + ud_asmprintf(u, ".byte 0x%x", u->operand[0].lval.ubyte); + return; + case UD_Ijmp: + case UD_Icall: + if (u->br_far) ud_asmprintf(u, "l"); + if (u->operand[0].type == UD_OP_REG) { + star = 1; + } + ud_asmprintf(u, "%s", ud_lookup_mnemonic(u->mnemonic)); + break; + case UD_Ibound: + case UD_Ienter: + if (u->operand[0].type != UD_NONE) + gen_operand(u, &u->operand[0]); + if (u->operand[1].type != UD_NONE) { + ud_asmprintf(u, ","); + gen_operand(u, &u->operand[1]); + } + return; + default: + ud_asmprintf(u, "%s", ud_lookup_mnemonic(u->mnemonic)); } - for (i = 3; i--;) { - if (u->operand[i].size > size - && u->operand[i].type != UD_OP_JIMM) - size = u->operand[i].size; + if (size == 8) { + ud_asmprintf(u, "b"); + } else if (size == 16) { + ud_asmprintf(u, "w"); + } else if (size == 64) { + ud_asmprintf(u, "q"); } - if (size == 8) - mkasm(u, "b"); - else if (size == 16) - mkasm(u, "w"); - else if (size == 32) - mkasm(u, "l"); - else if (size == 64) - mkasm(u, "q"); - - mkasm(u, " "); + if (star) { + ud_asmprintf(u, " *"); + } else { + ud_asmprintf(u, " "); + } + if (u->operand[3].type != UD_NONE) { + gen_operand(u, &u->operand[3]); + ud_asmprintf(u, ", "); + } if (u->operand[2].type != UD_NONE) { - gen_operand(u, &u->operand[2]); - mkasm(u, ", "); + gen_operand(u, &u->operand[2]); + ud_asmprintf(u, ", "); } - if (u->operand[1].type != UD_NONE) { - gen_operand(u, &u->operand[1]); - mkasm(u, ", "); + gen_operand(u, &u->operand[1]); + ud_asmprintf(u, ", "); + } + if (u->operand[0].type != UD_NONE) { + gen_operand(u, &u->operand[0]); } - - if (u->operand[0].type != UD_NONE) - gen_operand(u, &u->operand[0]); } #endif // USE(UDIS86) +/* +vim: set ts=2 sw=2 expandtab +*/ diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_syn-intel.c b/Source/JavaScriptCore/disassembler/udis86/udis86_syn-intel.c index 4ad42eb63..769df8901 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_syn-intel.c +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_syn-intel.c @@ -1,6 +1,6 @@ /* udis86 - libudis86/syn-intel.c * - * Copyright (c) 2002-2009 Vivek Thampi + * Copyright (c) 2002-2013 Vivek Thampi * All rights reserved. * * Redistribution and use in source and binary forms, with or without modification, @@ -23,6 +23,7 @@ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ + #include "config.h" #if USE(UDIS86) @@ -32,6 +33,7 @@ #include "udis86_decode.h" #include "udis86_itab.h" #include "udis86_syn.h" +#include "udis86_udint.h" /* ----------------------------------------------------------------------------- * opr_cast() - Prints an operand cast. @@ -40,16 +42,19 @@ static void opr_cast(struct ud* u, struct ud_operand* op) { + if (u->br_far) { + ud_asmprintf(u, "far "); + } switch(op->size) { - case 8: mkasm(u, "byte " ); break; - case 16: mkasm(u, "word " ); break; - case 32: mkasm(u, "dword "); break; - case 64: mkasm(u, "qword "); break; - case 80: mkasm(u, "tword "); break; - default: break; + case 8: ud_asmprintf(u, "byte " ); break; + case 16: ud_asmprintf(u, "word " ); break; + case 32: ud_asmprintf(u, "dword "); break; + case 64: ud_asmprintf(u, "qword "); break; + case 80: ud_asmprintf(u, "tword "); break; + case 128: ud_asmprintf(u, "oword "); break; + case 256: ud_asmprintf(u, "yword "); break; + default: break; } - if (u->br_far) - mkasm(u, "far "); } /* ----------------------------------------------------------------------------- @@ -59,121 +64,63 @@ opr_cast(struct ud* u, struct ud_operand* op) static void gen_operand(struct ud* u, struct ud_operand* op, int syn_cast) { switch(op->type) { - case UD_OP_REG: - mkasm(u, "%s", ud_reg_tab[op->base - UD_R_AL]); - break; - - case UD_OP_MEM: { - - int op_f = 0; - - if (syn_cast) - opr_cast(u, op); - - mkasm(u, "["); - - if (u->pfx_seg) - mkasm(u, "%s:", ud_reg_tab[u->pfx_seg - UD_R_AL]); - - if (op->base) { - mkasm(u, "%s", ud_reg_tab[op->base - UD_R_AL]); - op_f = 1; - } - - if (op->index) { - if (op_f) - mkasm(u, "+"); - mkasm(u, "%s", ud_reg_tab[op->index - UD_R_AL]); - op_f = 1; - } + case UD_OP_REG: + ud_asmprintf(u, "%s", ud_reg_tab[op->base - UD_R_AL]); + break; - if (op->scale) - mkasm(u, "*%d", op->scale); - - if (op->offset == 8) { - if (op->lval.sbyte < 0) - mkasm(u, "-0x%x", -op->lval.sbyte); - else mkasm(u, "%s0x%x", (op_f) ? "+" : "", op->lval.sbyte); - } - else if (op->offset == 16) - mkasm(u, "%s0x%x", (op_f) ? "+" : "", op->lval.uword); - else if (op->offset == 32) { - if (u->adr_mode == 64) { - if (op->lval.sdword < 0) - mkasm(u, "-0x%x", -op->lval.sdword); - else mkasm(u, "%s0x%x", (op_f) ? "+" : "", op->lval.sdword); - } - else mkasm(u, "%s0x%lx", (op_f) ? "+" : "", (unsigned long)op->lval.udword); - } - else if (op->offset == 64) - mkasm(u, "%s0x" FMT64 "x", (op_f) ? "+" : "", (uint64_t)op->lval.uqword); - - mkasm(u, "]"); - break; - } - - case UD_OP_IMM: { - int64_t imm = 0; - uint64_t sext_mask = 0xffffffffffffffffull; - unsigned sext_size = op->size; - - if (syn_cast) - opr_cast(u, op); - switch (op->size) { - case 8: imm = op->lval.sbyte; break; - case 16: imm = op->lval.sword; break; - case 32: imm = op->lval.sdword; break; - case 64: imm = op->lval.sqword; break; - } - if ( P_SEXT( u->itab_entry->prefix ) ) { - sext_size = u->operand[ 0 ].size; - if ( u->mnemonic == UD_Ipush ) - /* push sign-extends to operand size */ - sext_size = u->opr_mode; - } - if ( sext_size < 64 ) - sext_mask = ( 1ull << sext_size ) - 1; - mkasm( u, "0x" FMT64 "x", (uint64_t)(imm & sext_mask) ); - - break; + case UD_OP_MEM: + if (syn_cast) { + opr_cast(u, op); } + ud_asmprintf(u, "["); + if (u->pfx_seg) { + ud_asmprintf(u, "%s:", ud_reg_tab[u->pfx_seg - UD_R_AL]); + } + if (op->base) { + ud_asmprintf(u, "%s", ud_reg_tab[op->base - UD_R_AL]); + } + if (op->index) { + ud_asmprintf(u, "%s%s", op->base != UD_NONE? "+" : "", + ud_reg_tab[op->index - UD_R_AL]); + if (op->scale) { + ud_asmprintf(u, "*%d", op->scale); + } + } + if (op->offset != 0) { + ud_syn_print_mem_disp(u, op, (op->base != UD_NONE || + op->index != UD_NONE) ? 1 : 0); + } + ud_asmprintf(u, "]"); + break; + + case UD_OP_IMM: + ud_syn_print_imm(u, op); + break; + + + case UD_OP_JIMM: + ud_syn_print_addr(u, ud_syn_rel_target(u, op)); + break; + + case UD_OP_PTR: + switch (op->size) { + case 32: + ud_asmprintf(u, "word 0x%x:0x%x", op->lval.ptr.seg, + op->lval.ptr.off & 0xFFFF); + break; + case 48: + ud_asmprintf(u, "dword 0x%x:0x%x", op->lval.ptr.seg, + op->lval.ptr.off); + break; + } + break; + case UD_OP_CONST: + if (syn_cast) opr_cast(u, op); + ud_asmprintf(u, "%d", op->lval.udword); + break; - case UD_OP_JIMM: - if (syn_cast) opr_cast(u, op); - switch (op->size) { - case 8: - mkasm(u, "0x" FMT64 "x", (uint64_t)(u->pc + op->lval.sbyte)); - break; - case 16: - mkasm(u, "0x" FMT64 "x", (uint64_t)(( u->pc + op->lval.sword ) & 0xffff) ); - break; - case 32: - mkasm(u, "0x" FMT64 "x", (uint64_t)(( u->pc + op->lval.sdword ) & 0xfffffffful) ); - break; - default:break; - } - break; - - case UD_OP_PTR: - switch (op->size) { - case 32: - mkasm(u, "word 0x%x:0x%x", op->lval.ptr.seg, - op->lval.ptr.off & 0xFFFF); - break; - case 48: - mkasm(u, "dword 0x%x:0x%lx", op->lval.ptr.seg, - (unsigned long)op->lval.ptr.off); - break; - } - break; - - case UD_OP_CONST: - if (syn_cast) opr_cast(u, op); - mkasm(u, "%d", op->lval.udword); - break; - - default: return; + default: return; } } @@ -181,98 +128,104 @@ static void gen_operand(struct ud* u, struct ud_operand* op, int syn_cast) * translates to intel syntax * ============================================================================= */ -extern void ud_translate_intel(struct ud* u) +extern void +ud_translate_intel(struct ud* u) { - /* -- prefixes -- */ - /* check if P_OSO prefix is used */ - if (! P_OSO(u->itab_entry->prefix) && u->pfx_opr) { - switch (u->dis_mode) { - case 16: - mkasm(u, "o32 "); - break; - case 32: - case 64: - mkasm(u, "o16 "); - break; - } + if (!P_OSO(u->itab_entry->prefix) && u->pfx_opr) { + switch (u->dis_mode) { + case 16: ud_asmprintf(u, "o32 "); break; + case 32: + case 64: ud_asmprintf(u, "o16 "); break; + } } /* check if P_ASO prefix was used */ - if (! P_ASO(u->itab_entry->prefix) && u->pfx_adr) { - switch (u->dis_mode) { - case 16: - mkasm(u, "a32 "); - break; - case 32: - mkasm(u, "a16 "); - break; - case 64: - mkasm(u, "a32 "); - break; - } + if (!P_ASO(u->itab_entry->prefix) && u->pfx_adr) { + switch (u->dis_mode) { + case 16: ud_asmprintf(u, "a32 "); break; + case 32: ud_asmprintf(u, "a16 "); break; + case 64: ud_asmprintf(u, "a32 "); break; + } } - if ( u->pfx_seg && - u->operand[0].type != UD_OP_MEM && - u->operand[1].type != UD_OP_MEM ) { - mkasm(u, "%s ", ud_reg_tab[u->pfx_seg - UD_R_AL]); - } - if (u->pfx_lock) - mkasm(u, "lock "); - if (u->pfx_rep) - mkasm(u, "rep "); - if (u->pfx_repne) - mkasm(u, "repne "); + if (u->pfx_seg && + u->operand[0].type != UD_OP_MEM && + u->operand[1].type != UD_OP_MEM ) { + ud_asmprintf(u, "%s ", ud_reg_tab[u->pfx_seg - UD_R_AL]); + } + + if (u->pfx_lock) { + ud_asmprintf(u, "lock "); + } + if (u->pfx_rep) { + ud_asmprintf(u, "rep "); + } else if (u->pfx_repe) { + ud_asmprintf(u, "repe "); + } else if (u->pfx_repne) { + ud_asmprintf(u, "repne "); + } /* print the instruction mnemonic */ - mkasm(u, "%s ", ud_lookup_mnemonic(u->mnemonic)); + ud_asmprintf(u, "%s", ud_lookup_mnemonic(u->mnemonic)); - /* operand 1 */ if (u->operand[0].type != UD_NONE) { int cast = 0; - if ( u->operand[0].type == UD_OP_IMM && - u->operand[1].type == UD_NONE ) - cast = u->c1; - if ( u->operand[0].type == UD_OP_MEM ) { - cast = u->c1; - if ( u->operand[1].type == UD_OP_IMM || - u->operand[1].type == UD_OP_CONST ) - cast = 1; - if ( u->operand[1].type == UD_NONE ) - cast = 1; - if ( ( u->operand[0].size != u->operand[1].size ) && u->operand[1].size ) - cast = 1; - } else if ( u->operand[ 0 ].type == UD_OP_JIMM ) { - if ( u->operand[ 0 ].size > 8 ) cast = 1; + ud_asmprintf(u, " "); + if (u->operand[0].type == UD_OP_MEM) { + if (u->operand[1].type == UD_OP_IMM || + u->operand[1].type == UD_OP_CONST || + u->operand[1].type == UD_NONE || + (u->operand[0].size != u->operand[1].size)) { + cast = 1; + } else if (u->operand[1].type == UD_OP_REG && + u->operand[1].base == UD_R_CL) { + switch (u->mnemonic) { + case UD_Ircl: + case UD_Irol: + case UD_Iror: + case UD_Ircr: + case UD_Ishl: + case UD_Ishr: + case UD_Isar: + cast = 1; + break; + default: break; + } + } } - gen_operand(u, &u->operand[0], cast); + gen_operand(u, &u->operand[0], cast); } - /* operand 2 */ + if (u->operand[1].type != UD_NONE) { int cast = 0; - mkasm(u, ", "); - if ( u->operand[1].type == UD_OP_MEM ) { - cast = u->c1; - - if ( u->operand[0].type != UD_OP_REG ) - cast = 1; - if ( u->operand[0].size != u->operand[1].size && u->operand[1].size ) - cast = 1; - if ( u->operand[0].type == UD_OP_REG && - u->operand[0].base >= UD_R_ES && - u->operand[0].base <= UD_R_GS ) - cast = 0; + ud_asmprintf(u, ", "); + if (u->operand[1].type == UD_OP_MEM && + u->operand[0].size != u->operand[1].size && + !ud_opr_is_sreg(&u->operand[0])) { + cast = 1; } - gen_operand(u, &u->operand[1], cast ); + gen_operand(u, &u->operand[1], cast); } - /* operand 3 */ if (u->operand[2].type != UD_NONE) { - mkasm(u, ", "); - gen_operand(u, &u->operand[2], u->c3); + int cast = 0; + ud_asmprintf(u, ", "); + if (u->operand[2].type == UD_OP_MEM && + u->operand[2].size != u->operand[1].size) { + cast = 1; + } + gen_operand(u, &u->operand[2], cast); + } + + if (u->operand[3].type != UD_NONE) { + ud_asmprintf(u, ", "); + gen_operand(u, &u->operand[3], 0); } } #endif // USE(UDIS86) +/* +vim: set ts=2 sw=2 expandtab +*/ diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_syn.c b/Source/JavaScriptCore/disassembler/udis86/udis86_syn.c index 31a45ea5c..4417d9997 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_syn.c +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_syn.c @@ -1,6 +1,6 @@ /* udis86 - libudis86/syn.c * - * Copyright (c) 2002-2009 Vivek Thampi + * Copyright (c) 2002-2013 Vivek Thampi * All rights reserved. * * Redistribution and use in source and binary forms, with or without modification, @@ -28,59 +28,192 @@ #if USE(UDIS86) -/* ----------------------------------------------------------------------------- - * Intel Register Table - Order Matters (types.h)! - * ----------------------------------------------------------------------------- +#include "udis86_types.h" +#include "udis86_decode.h" +#include "udis86_syn.h" +#include "udis86_udint.h" + +/* + * Register Table - Order Matters (types.h)! + * */ const char* ud_reg_tab[] = { - "al", "cl", "dl", "bl", - "ah", "ch", "dh", "bh", - "spl", "bpl", "sil", "dil", - "r8b", "r9b", "r10b", "r11b", - "r12b", "r13b", "r14b", "r15b", - - "ax", "cx", "dx", "bx", - "sp", "bp", "si", "di", - "r8w", "r9w", "r10w", "r11w", - "r12w", "r13W" , "r14w", "r15w", - - "eax", "ecx", "edx", "ebx", - "esp", "ebp", "esi", "edi", - "r8d", "r9d", "r10d", "r11d", - "r12d", "r13d", "r14d", "r15d", - - "rax", "rcx", "rdx", "rbx", - "rsp", "rbp", "rsi", "rdi", - "r8", "r9", "r10", "r11", - "r12", "r13", "r14", "r15", - - "es", "cs", "ss", "ds", - "fs", "gs", - - "cr0", "cr1", "cr2", "cr3", - "cr4", "cr5", "cr6", "cr7", - "cr8", "cr9", "cr10", "cr11", - "cr12", "cr13", "cr14", "cr15", - - "dr0", "dr1", "dr2", "dr3", - "dr4", "dr5", "dr6", "dr7", - "dr8", "dr9", "dr10", "dr11", - "dr12", "dr13", "dr14", "dr15", - - "mm0", "mm1", "mm2", "mm3", - "mm4", "mm5", "mm6", "mm7", - - "st0", "st1", "st2", "st3", - "st4", "st5", "st6", "st7", - - "xmm0", "xmm1", "xmm2", "xmm3", - "xmm4", "xmm5", "xmm6", "xmm7", - "xmm8", "xmm9", "xmm10", "xmm11", - "xmm12", "xmm13", "xmm14", "xmm15", + "al", "cl", "dl", "bl", + "ah", "ch", "dh", "bh", + "spl", "bpl", "sil", "dil", + "r8b", "r9b", "r10b", "r11b", + "r12b", "r13b", "r14b", "r15b", + + "ax", "cx", "dx", "bx", + "sp", "bp", "si", "di", + "r8w", "r9w", "r10w", "r11w", + "r12w", "r13w", "r14w", "r15w", + + "eax", "ecx", "edx", "ebx", + "esp", "ebp", "esi", "edi", + "r8d", "r9d", "r10d", "r11d", + "r12d", "r13d", "r14d", "r15d", + + "rax", "rcx", "rdx", "rbx", + "rsp", "rbp", "rsi", "rdi", + "r8", "r9", "r10", "r11", + "r12", "r13", "r14", "r15", + + "es", "cs", "ss", "ds", + "fs", "gs", + + "cr0", "cr1", "cr2", "cr3", + "cr4", "cr5", "cr6", "cr7", + "cr8", "cr9", "cr10", "cr11", + "cr12", "cr13", "cr14", "cr15", + + "dr0", "dr1", "dr2", "dr3", + "dr4", "dr5", "dr6", "dr7", + "dr8", "dr9", "dr10", "dr11", + "dr12", "dr13", "dr14", "dr15", + + "mm0", "mm1", "mm2", "mm3", + "mm4", "mm5", "mm6", "mm7", + + "st0", "st1", "st2", "st3", + "st4", "st5", "st6", "st7", + + "xmm0", "xmm1", "xmm2", "xmm3", + "xmm4", "xmm5", "xmm6", "xmm7", + "xmm8", "xmm9", "xmm10", "xmm11", + "xmm12", "xmm13", "xmm14", "xmm15", + + "ymm0", "ymm1", "ymm2", "ymm3", + "ymm4", "ymm5", "ymm6", "ymm7", + "ymm8", "ymm9", "ymm10", "ymm11", + "ymm12", "ymm13", "ymm14", "ymm15", "rip" }; + +uint64_t +ud_syn_rel_target(struct ud *u, struct ud_operand *opr) +{ + const uint64_t trunc_mask = 0xffffffffffffffffull >> (64 - u->opr_mode); + switch (opr->size) { + case 8 : return (u->pc + opr->lval.sbyte) & trunc_mask; + case 16: return (u->pc + opr->lval.sword) & trunc_mask; + case 32: return (u->pc + opr->lval.sdword) & trunc_mask; + default: UD_ASSERT(!"invalid relative offset size."); + return 0ull; + } +} + + +/* + * asmprintf + * Printf style function for printing translated assembly + * output. Returns the number of characters written and + * moves the buffer pointer forward. On an overflow, + * returns a negative number and truncates the output. + */ +int +ud_asmprintf(struct ud *u, const char *fmt, ...) +{ + int ret; + int avail; + va_list ap; + va_start(ap, fmt); + avail = u->asm_buf_size - u->asm_buf_fill - 1 /* nullchar */; + ret = vsnprintf((char*) u->asm_buf + u->asm_buf_fill, avail, fmt, ap); + if (ret < 0 || ret > avail) { + u->asm_buf_fill = u->asm_buf_size - 1; + } else { + u->asm_buf_fill += ret; + } + va_end(ap); + return ret; +} + + +void +ud_syn_print_addr(struct ud *u, uint64_t addr) +{ + const char *name = NULL; + if (u->sym_resolver) { + int64_t offset = 0; + name = u->sym_resolver(u, addr, &offset); + if (name) { + if (offset) { + ud_asmprintf(u, "%s%+" FMT64 "d", name, offset); + } else { + ud_asmprintf(u, "%s", name); + } + return; + } + } + ud_asmprintf(u, "0x%" FMT64 "x", addr); +} + + +void +ud_syn_print_imm(struct ud* u, const struct ud_operand *op) +{ + uint64_t v; + if (op->_oprcode == OP_sI && op->size != u->opr_mode) { + if (op->size == 8) { + v = (int64_t)op->lval.sbyte; + } else { + UD_ASSERT(op->size == 32); + v = (int64_t)op->lval.sdword; + } + if (u->opr_mode < 64) { + v = v & ((1ull << u->opr_mode) - 1ull); + } + } else { + switch (op->size) { + case 8 : v = op->lval.ubyte; break; + case 16: v = op->lval.uword; break; + case 32: v = op->lval.udword; break; + case 64: v = op->lval.uqword; break; + default: UD_ASSERT(!"invalid offset"); v = 0; /* keep cc happy */ + } + } + ud_asmprintf(u, "0x%" FMT64 "x", v); +} + + +void +ud_syn_print_mem_disp(struct ud* u, const struct ud_operand *op, int sign) +{ + UD_ASSERT(op->offset != 0); + if (op->base == UD_NONE && op->index == UD_NONE) { + uint64_t v; + UD_ASSERT(op->scale == UD_NONE && op->offset != 8); + /* unsigned mem-offset */ + switch (op->offset) { + case 16: v = op->lval.uword; break; + case 32: v = op->lval.udword; break; + case 64: v = op->lval.uqword; break; + default: UD_ASSERT(!"invalid offset"); v = 0; /* keep cc happy */ + } + ud_asmprintf(u, "0x%" FMT64 "x", v); + } else { + int64_t v; + UD_ASSERT(op->offset != 64); + switch (op->offset) { + case 8 : v = op->lval.sbyte; break; + case 16: v = op->lval.sword; break; + case 32: v = op->lval.sdword; break; + default: UD_ASSERT(!"invalid offset"); v = 0; /* keep cc happy */ + } + if (v < 0) { + ud_asmprintf(u, "-0x%" FMT64 "x", -v); + } else if (v > 0) { + ud_asmprintf(u, "%s0x%" FMT64 "x", sign? "+" : "", v); + } + } +} + #endif // USE(UDIS86) +/* +vim: set ts=2 sw=2 expandtab +*/ diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_syn.h b/Source/JavaScriptCore/disassembler/udis86/udis86_syn.h index e8636163e..712ec37ae 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_syn.h +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_syn.h @@ -27,21 +27,27 @@ #define UD_SYN_H #include "udis86_types.h" -#include - #ifndef __UD_STANDALONE__ # include #endif /* __UD_STANDALONE__ */ extern const char* ud_reg_tab[]; -static void mkasm(struct ud* u, const char* fmt, ...) WTF_ATTRIBUTE_PRINTF(2, 3); -static void mkasm(struct ud* u, const char* fmt, ...) -{ - va_list ap; - va_start(ap, fmt); - u->insn_fill += vsnprintf((char*) u->insn_buffer + u->insn_fill, UD_STRING_BUFFER_SIZE - u->insn_fill, fmt, ap); - va_end(ap); -} +uint64_t ud_syn_rel_target(struct ud*, struct ud_operand*); +#ifdef __GNUC__ +int ud_asmprintf(struct ud *u, const char *fmt, ...) + __attribute__ ((format (printf, 2, 3))); +#else +int ud_asmprintf(struct ud *u, const char *fmt, ...); #endif + +void ud_syn_print_addr(struct ud *u, uint64_t addr); +void ud_syn_print_imm(struct ud* u, const struct ud_operand *op); +void ud_syn_print_mem_disp(struct ud* u, const struct ud_operand *, int sign); + +#endif /* UD_SYN_H */ + +/* +vim: set ts=2 sw=2 expandtab +*/ diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_types.h b/Source/JavaScriptCore/disassembler/udis86/udis86_types.h index 176bf6d73..604f08e51 100644 --- a/Source/JavaScriptCore/disassembler/udis86/udis86_types.h +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_types.h @@ -1,6 +1,6 @@ /* udis86 - libudis86/types.h * - * Copyright (c) 2002-2009 Vivek Thampi + * Copyright (c) 2002-2013 Vivek Thampi * All rights reserved. * * Redistribution and use in source and binary forms, with or without modification, @@ -26,9 +26,23 @@ #ifndef UD_TYPES_H #define UD_TYPES_H -#ifndef __UD_STANDALONE__ +#ifdef __KERNEL__ + /* + * -D__KERNEL__ is automatically passed on the command line when + * building something as part of the Linux kernel. Assume standalone + * mode. + */ +# include +# include +# ifndef __UD_STANDALONE__ +# define __UD_STANDALONE__ 1 +# endif +#endif /* __KERNEL__ */ + +#if !defined(__UD_STANDALONE__) +# include # include -#endif /* __UD_STANDALONE__ */ +#endif /* gcc specific extensions */ #ifdef __GNUC__ @@ -37,26 +51,6 @@ # define UD_ATTR_PACKED #endif /* UD_ATTR_PACKED */ -#ifdef _MSC_VER -# define FMT64 "%I64" - typedef unsigned __int8 uint8_t; - typedef unsigned __int16 uint16_t; - typedef unsigned __int32 uint32_t; - typedef unsigned __int64 uint64_t; - typedef __int8 int8_t; - typedef __int16 int16_t; - typedef __int32 int32_t; - typedef __int64 int64_t; -#else -# if defined(__GNU_LIBRARY__) && defined(__WORDSIZE) && (__WORDSIZE == 64) -# define FMT64 "%l" -# else -# define FMT64 "%ll" -# endif -# ifndef __UD_STANDALONE__ -# include -# endif /* __UD_STANDALONE__ */ -#endif /* ----------------------------------------------------------------------------- * All possible "types" of objects in udis86. Order is Important! @@ -67,152 +61,176 @@ enum ud_type UD_NONE, /* 8 bit GPRs */ - UD_R_AL, UD_R_CL, UD_R_DL, UD_R_BL, - UD_R_AH, UD_R_CH, UD_R_DH, UD_R_BH, - UD_R_SPL, UD_R_BPL, UD_R_SIL, UD_R_DIL, - UD_R_R8B, UD_R_R9B, UD_R_R10B, UD_R_R11B, - UD_R_R12B, UD_R_R13B, UD_R_R14B, UD_R_R15B, + UD_R_AL, UD_R_CL, UD_R_DL, UD_R_BL, + UD_R_AH, UD_R_CH, UD_R_DH, UD_R_BH, + UD_R_SPL, UD_R_BPL, UD_R_SIL, UD_R_DIL, + UD_R_R8B, UD_R_R9B, UD_R_R10B, UD_R_R11B, + UD_R_R12B, UD_R_R13B, UD_R_R14B, UD_R_R15B, /* 16 bit GPRs */ - UD_R_AX, UD_R_CX, UD_R_DX, UD_R_BX, - UD_R_SP, UD_R_BP, UD_R_SI, UD_R_DI, - UD_R_R8W, UD_R_R9W, UD_R_R10W, UD_R_R11W, - UD_R_R12W, UD_R_R13W, UD_R_R14W, UD_R_R15W, - + UD_R_AX, UD_R_CX, UD_R_DX, UD_R_BX, + UD_R_SP, UD_R_BP, UD_R_SI, UD_R_DI, + UD_R_R8W, UD_R_R9W, UD_R_R10W, UD_R_R11W, + UD_R_R12W, UD_R_R13W, UD_R_R14W, UD_R_R15W, + /* 32 bit GPRs */ - UD_R_EAX, UD_R_ECX, UD_R_EDX, UD_R_EBX, - UD_R_ESP, UD_R_EBP, UD_R_ESI, UD_R_EDI, - UD_R_R8D, UD_R_R9D, UD_R_R10D, UD_R_R11D, - UD_R_R12D, UD_R_R13D, UD_R_R14D, UD_R_R15D, - + UD_R_EAX, UD_R_ECX, UD_R_EDX, UD_R_EBX, + UD_R_ESP, UD_R_EBP, UD_R_ESI, UD_R_EDI, + UD_R_R8D, UD_R_R9D, UD_R_R10D, UD_R_R11D, + UD_R_R12D, UD_R_R13D, UD_R_R14D, UD_R_R15D, + /* 64 bit GPRs */ - UD_R_RAX, UD_R_RCX, UD_R_RDX, UD_R_RBX, - UD_R_RSP, UD_R_RBP, UD_R_RSI, UD_R_RDI, - UD_R_R8, UD_R_R9, UD_R_R10, UD_R_R11, - UD_R_R12, UD_R_R13, UD_R_R14, UD_R_R15, + UD_R_RAX, UD_R_RCX, UD_R_RDX, UD_R_RBX, + UD_R_RSP, UD_R_RBP, UD_R_RSI, UD_R_RDI, + UD_R_R8, UD_R_R9, UD_R_R10, UD_R_R11, + UD_R_R12, UD_R_R13, UD_R_R14, UD_R_R15, /* segment registers */ - UD_R_ES, UD_R_CS, UD_R_SS, UD_R_DS, - UD_R_FS, UD_R_GS, + UD_R_ES, UD_R_CS, UD_R_SS, UD_R_DS, + UD_R_FS, UD_R_GS, /* control registers*/ - UD_R_CR0, UD_R_CR1, UD_R_CR2, UD_R_CR3, - UD_R_CR4, UD_R_CR5, UD_R_CR6, UD_R_CR7, - UD_R_CR8, UD_R_CR9, UD_R_CR10, UD_R_CR11, - UD_R_CR12, UD_R_CR13, UD_R_CR14, UD_R_CR15, - + UD_R_CR0, UD_R_CR1, UD_R_CR2, UD_R_CR3, + UD_R_CR4, UD_R_CR5, UD_R_CR6, UD_R_CR7, + UD_R_CR8, UD_R_CR9, UD_R_CR10, UD_R_CR11, + UD_R_CR12, UD_R_CR13, UD_R_CR14, UD_R_CR15, + /* debug registers */ - UD_R_DR0, UD_R_DR1, UD_R_DR2, UD_R_DR3, - UD_R_DR4, UD_R_DR5, UD_R_DR6, UD_R_DR7, - UD_R_DR8, UD_R_DR9, UD_R_DR10, UD_R_DR11, - UD_R_DR12, UD_R_DR13, UD_R_DR14, UD_R_DR15, + UD_R_DR0, UD_R_DR1, UD_R_DR2, UD_R_DR3, + UD_R_DR4, UD_R_DR5, UD_R_DR6, UD_R_DR7, + UD_R_DR8, UD_R_DR9, UD_R_DR10, UD_R_DR11, + UD_R_DR12, UD_R_DR13, UD_R_DR14, UD_R_DR15, /* mmx registers */ - UD_R_MM0, UD_R_MM1, UD_R_MM2, UD_R_MM3, - UD_R_MM4, UD_R_MM5, UD_R_MM6, UD_R_MM7, + UD_R_MM0, UD_R_MM1, UD_R_MM2, UD_R_MM3, + UD_R_MM4, UD_R_MM5, UD_R_MM6, UD_R_MM7, /* x87 registers */ - UD_R_ST0, UD_R_ST1, UD_R_ST2, UD_R_ST3, - UD_R_ST4, UD_R_ST5, UD_R_ST6, UD_R_ST7, + UD_R_ST0, UD_R_ST1, UD_R_ST2, UD_R_ST3, + UD_R_ST4, UD_R_ST5, UD_R_ST6, UD_R_ST7, /* extended multimedia registers */ - UD_R_XMM0, UD_R_XMM1, UD_R_XMM2, UD_R_XMM3, - UD_R_XMM4, UD_R_XMM5, UD_R_XMM6, UD_R_XMM7, - UD_R_XMM8, UD_R_XMM9, UD_R_XMM10, UD_R_XMM11, - UD_R_XMM12, UD_R_XMM13, UD_R_XMM14, UD_R_XMM15, + UD_R_XMM0, UD_R_XMM1, UD_R_XMM2, UD_R_XMM3, + UD_R_XMM4, UD_R_XMM5, UD_R_XMM6, UD_R_XMM7, + UD_R_XMM8, UD_R_XMM9, UD_R_XMM10, UD_R_XMM11, + UD_R_XMM12, UD_R_XMM13, UD_R_XMM14, UD_R_XMM15, + + /* 256B multimedia registers */ + UD_R_YMM0, UD_R_YMM1, UD_R_YMM2, UD_R_YMM3, + UD_R_YMM4, UD_R_YMM5, UD_R_YMM6, UD_R_YMM7, + UD_R_YMM8, UD_R_YMM9, UD_R_YMM10, UD_R_YMM11, + UD_R_YMM12, UD_R_YMM13, UD_R_YMM14, UD_R_YMM15, UD_R_RIP, /* Operand Types */ - UD_OP_REG, UD_OP_MEM, UD_OP_PTR, UD_OP_IMM, - UD_OP_JIMM, UD_OP_CONST + UD_OP_REG, UD_OP_MEM, UD_OP_PTR, UD_OP_IMM, + UD_OP_JIMM, UD_OP_CONST }; #include "udis86_itab.h" +union ud_lval { + int8_t sbyte; + uint8_t ubyte; + int16_t sword; + uint16_t uword; + int32_t sdword; + uint32_t udword; + int64_t sqword; + uint64_t uqword; + struct { + uint16_t seg; + uint32_t off; + } ptr; +}; + /* ----------------------------------------------------------------------------- * struct ud_operand - Disassembled instruction Operand. * ----------------------------------------------------------------------------- */ -struct ud_operand -{ - enum ud_type type; - uint8_t size; - union { - int8_t sbyte; - uint8_t ubyte; - int16_t sword; - uint16_t uword; - int32_t sdword; - uint32_t udword; - int64_t sqword; - uint64_t uqword; - - struct { - uint16_t seg; - uint32_t off; - } ptr; - } lval; - - enum ud_type base; - enum ud_type index; - uint8_t offset; - uint8_t scale; +struct ud_operand { + enum ud_type type; + uint16_t size; + enum ud_type base; + enum ud_type index; + uint8_t scale; + uint8_t offset; + union ud_lval lval; + /* + * internal use only + */ + uint64_t _legacy; /* this will be removed in 1.8 */ + uint8_t _oprcode; }; -#define UD_STRING_BUFFER_SIZE 64 - /* ----------------------------------------------------------------------------- * struct ud - The udis86 object. * ----------------------------------------------------------------------------- */ struct ud { - int (*inp_hook) (struct ud*); - uint8_t inp_curr; - uint8_t inp_fill; + /* + * input buffering + */ + int (*inp_hook) (struct ud*); #ifndef __UD_STANDALONE__ - FILE* inp_file; + FILE* inp_file; #endif - uint8_t inp_ctr; - uint8_t* inp_buff; - uint8_t* inp_buff_end; - uint8_t inp_end; - void (*translator)(struct ud*); - uint64_t insn_offset; - char insn_hexcode[32]; - char insn_buffer[UD_STRING_BUFFER_SIZE]; - unsigned int insn_fill; - uint8_t dis_mode; - uint64_t pc; - uint8_t vendor; - struct map_entry* mapen; - enum ud_mnemonic_code mnemonic; - struct ud_operand operand[3]; - uint8_t error; - uint8_t pfx_rex; - uint8_t pfx_seg; - uint8_t pfx_opr; - uint8_t pfx_adr; - uint8_t pfx_lock; - uint8_t pfx_rep; - uint8_t pfx_repe; - uint8_t pfx_repne; - uint8_t pfx_insn; - uint8_t default64; - uint8_t opr_mode; - uint8_t adr_mode; - uint8_t br_far; - uint8_t br_near; - uint8_t implicit_addr; - uint8_t c1; - uint8_t c2; - uint8_t c3; - uint8_t inp_cache[256]; - uint8_t inp_sess[64]; - uint8_t have_modrm; - uint8_t modrm; - void * user_opaque_data; + const uint8_t* inp_buf; + size_t inp_buf_size; + size_t inp_buf_index; + uint8_t inp_curr; + size_t inp_ctr; + uint8_t inp_sess[64]; + int inp_end; + int inp_peek; + + void (*translator)(struct ud*); + uint64_t insn_offset; + char insn_hexcode[64]; + + /* + * Assembly output buffer + */ + char *asm_buf; + size_t asm_buf_size; + size_t asm_buf_fill; + char asm_buf_int[128]; + + /* + * Symbol resolver for use in the translation phase. + */ + const char* (*sym_resolver)(struct ud*, uint64_t addr, int64_t *offset); + + uint8_t dis_mode; + uint64_t pc; + uint8_t vendor; + enum ud_mnemonic_code mnemonic; + struct ud_operand operand[4]; + uint8_t error; + uint8_t _rex; + uint8_t pfx_rex; + uint8_t pfx_seg; + uint8_t pfx_opr; + uint8_t pfx_adr; + uint8_t pfx_lock; + uint8_t pfx_str; + uint8_t pfx_rep; + uint8_t pfx_repe; + uint8_t pfx_repne; + uint8_t opr_mode; + uint8_t adr_mode; + uint8_t br_far; + uint8_t br_near; + uint8_t have_modrm; + uint8_t modrm; + uint8_t modrm_offset; + uint8_t vex_op; + uint8_t vex_b1; + uint8_t vex_b2; + uint8_t primary_opcode; + void * user_opaque_data; struct ud_itab_entry * itab_entry; struct ud_lookup_table_list_entry *le; }; @@ -221,22 +239,22 @@ struct ud * Type-definitions * ----------------------------------------------------------------------------- */ -typedef enum ud_type ud_type_t; -typedef enum ud_mnemonic_code ud_mnemonic_code_t; +typedef enum ud_type ud_type_t; +typedef enum ud_mnemonic_code ud_mnemonic_code_t; -typedef struct ud ud_t; -typedef struct ud_operand ud_operand_t; +typedef struct ud ud_t; +typedef struct ud_operand ud_operand_t; -#define UD_SYN_INTEL ud_translate_intel -#define UD_SYN_ATT ud_translate_att -#define UD_EOI -1 -#define UD_INP_CACHE_SZ 32 -#define UD_VENDOR_AMD 0 -#define UD_VENDOR_INTEL 1 -#define UD_VENDOR_ANY 2 - -#define bail_out(ud,error_code) longjmp( (ud)->bailout, error_code ) -#define try_decode(ud) if ( setjmp( (ud)->bailout ) == 0 ) -#define catch_error() else +#define UD_SYN_INTEL ud_translate_intel +#define UD_SYN_ATT ud_translate_att +#define UD_EOI (-1) +#define UD_INP_CACHE_SZ 32 +#define UD_VENDOR_AMD 0 +#define UD_VENDOR_INTEL 1 +#define UD_VENDOR_ANY 2 #endif + +/* +vim: set ts=2 sw=2 expandtab +*/ diff --git a/Source/JavaScriptCore/disassembler/udis86/udis86_udint.h b/Source/JavaScriptCore/disassembler/udis86/udis86_udint.h new file mode 100644 index 000000000..d166b9173 --- /dev/null +++ b/Source/JavaScriptCore/disassembler/udis86/udis86_udint.h @@ -0,0 +1,98 @@ +/* udis86 - libudis86/udint.h -- definitions for internal use only + * + * Copyright (c) 2002-2009 Vivek Thampi + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * * Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR + * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON + * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +#ifndef _UDINT_H_ +#define _UDINT_H_ + +#include "udis86_types.h" + +#ifdef HAVE_CONFIG_H +# include +#endif /* HAVE_CONFIG_H */ + +#if defined(UD_DEBUG) && HAVE_ASSERT_H +# define UD_ASSERT(_x) ASSERT(_x) +#else +# define UD_ASSERT(_x) +#endif /* !HAVE_ASSERT_H */ + +#if defined(UD_DEBUG) + #define UDERR(u, msg) \ + do { \ + (u)->error = 1; \ + fprintf(stderr, "decode-error: %s:%d: %s", \ + __FILE__, __LINE__, (msg)); \ + } while (0) +#else + #define UDERR(u, m) \ + do { \ + (u)->error = 1; \ + } while (0) +#endif /* !LOGERR */ + +#define UD_RETURN_ON_ERROR(u) \ + do { \ + if ((u)->error != 0) { \ + return (u)->error; \ + } \ + } while (0) + +#define UD_RETURN_WITH_ERROR(u, m) \ + do { \ + UDERR(u, m); \ + return (u)->error; \ + } while (0) + +#ifndef __UD_STANDALONE__ +# define UD_NON_STANDALONE(x) x +#else +# define UD_NON_STANDALONE(x) +#endif + +/* printf formatting int64 specifier */ +#ifdef FMT64 +# undef FMT64 +#endif +#if defined(_MSC_VER) || defined(__BORLANDC__) +# define FMT64 "I64" +#else +# if defined(__APPLE__) +# define FMT64 "ll" +# elif defined(__amd64__) || defined(__x86_64__) +# define FMT64 "l" +# else +# define FMT64 "ll" +# endif /* !x64 */ +#endif + +/* define an inline macro */ +#if defined(_MSC_VER) || defined(__BORLANDC__) +# define UD_INLINE __inline /* MS Visual Studio requires __inline + instead of inline for C code */ +#else +# define UD_INLINE inline +#endif + +#endif /* _UDINT_H_ */ diff --git a/Source/JavaScriptCore/jit/ExecutableAllocator.h b/Source/JavaScriptCore/jit/ExecutableAllocator.h index c5bc122eb..015ac8968 100644 --- a/Source/JavaScriptCore/jit/ExecutableAllocator.h +++ b/Source/JavaScriptCore/jit/ExecutableAllocator.h @@ -76,7 +76,7 @@ class DemandExecutableAllocator; #if ENABLE(EXECUTABLE_ALLOCATOR_FIXED) #if defined(FIXED_EXECUTABLE_MEMORY_POOL_SIZE_IN_MB) && FIXED_EXECUTABLE_MEMORY_POOL_SIZE_IN_MB > 0 static const size_t fixedExecutableMemoryPoolSize = FIXED_EXECUTABLE_MEMORY_POOL_SIZE_IN_MB * 1024 * 1024; -#elif CPU(ARM) +#elif CPU(ARM) || CPU(MIPS) static const size_t fixedExecutableMemoryPoolSize = 16 * 1024 * 1024; #elif CPU(ARM64) static const size_t fixedExecutableMemoryPoolSize = 32 * 1024 * 1024; diff --git a/Source/WTF/wtf/OSAllocatorPosix.cpp b/Source/WTF/wtf/OSAllocatorPosix.cpp index f5e6669a9..0a07be635 100644 --- a/Source/WTF/wtf/OSAllocatorPosix.cpp +++ b/Source/WTF/wtf/OSAllocatorPosix.cpp @@ -35,17 +35,54 @@ namespace WTF { +#if CPU(MIPS) +static bool isWithin256MB(const void* ptr, size_t length) +{ + const intptr_t start = reinterpret_cast(ptr); + const intptr_t end = start + length - 1; + return (start & 0xf0000000) == (end & 0xf0000000); +} +#endif // CPU(MIPS) + void* OSAllocator::reserveUncommitted(size_t bytes, Usage usage, bool writable, bool executable, bool includesGuardPages) { #if OS(LINUX) UNUSED_PARAM(usage); UNUSED_PARAM(writable); +#if !CPU(MIPS) UNUSED_PARAM(executable); +#endif UNUSED_PARAM(includesGuardPages); void* result = mmap(0, bytes, PROT_NONE, MAP_NORESERVE | MAP_PRIVATE | MAP_ANON, -1, 0); if (result == MAP_FAILED) CRASH(); +#if CPU(MIPS) + // On MIPS we can use shorter j
jump instructions if the executable + // memory resides entirely within a single 256MB page (e.g. 0x3000.0000 to 0x3fff.ffff). + // Usually this is true for the small buffers we allocate, but we test, and upon failure + // we reallocate a double-size region, choose a valid region, and unmap the remainder. + if (executable && UNLIKELY(!isWithin256MB(result, bytes))) { + // Not in 256MB region, try to map double size. + if (munmap(result, bytes)) + CRASH(); + result = mmap(0, 2 * bytes, PROT_NONE, MAP_NORESERVE | MAP_PRIVATE | MAP_ANON, -1, 0); + if (result == MAP_FAILED) + CRASH(); + if (isWithin256MB(result, bytes)) { + // 1st half is good, release 2nd half. + if (munmap(reinterpret_cast(result) + bytes, bytes)) + CRASH(); + } else if (isWithin256MB(reinterpret_cast(result) + bytes, bytes)) { + // 2nd half is good, release 1st half. + if (munmap(result, bytes)) + CRASH(); + result = reinterpret_cast(result) + bytes; + } else + ASSERT_NOT_REACHED(); + } +#endif // CPU(MIPS) + madvise(result, bytes, MADV_DONTNEED); #else void* result = reserveAndCommit(bytes, usage, writable, executable, includesGuardPages); diff --git a/Source/WTF/wtf/Platform.h b/Source/WTF/wtf/Platform.h index 3f2069e7c..f3d725217 100644 --- a/Source/WTF/wtf/Platform.h +++ b/Source/WTF/wtf/Platform.h @@ -626,12 +626,6 @@ #define HAVE_PTHREAD_NP_H 1 #endif -#if !defined(HAVE_VASPRINTF) -#if !COMPILER(MSVC) && !COMPILER(MINGW) -#define HAVE_VASPRINTF 1 -#endif -#endif - #if !defined(HAVE_STRNSTR) #if OS(DARWIN) || (OS(FREEBSD) && !defined(__GLIBC__)) #define HAVE_STRNSTR 1 @@ -900,7 +894,7 @@ /* Pick which allocator to use; we only need an executable allocator if the assembler is compiled in. On non-Windows x86-64, iOS, and ARM64 we use a single fixed mmap, on other platforms we mmap on demand. */ #if ENABLE(ASSEMBLER) -#if CPU(X86_64) || PLATFORM(IOS) || CPU(ARM64) +#if CPU(X86_64) || PLATFORM(IOS) || CPU(ARM64) || CPU(MIPS) #define ENABLE_EXECUTABLE_ALLOCATOR_FIXED 1 #else #define ENABLE_EXECUTABLE_ALLOCATOR_DEMAND 1 @@ -1130,10 +1124,6 @@ #if COMPILER(MSVC) #undef __STDC_LIMIT_MACROS #define __STDC_LIMIT_MACROS -#if _MSC_VER < 1900 -#undef _HAS_EXCEPTIONS -#define _HAS_EXCEPTIONS 1 -#endif #endif #if PLATFORM(MAC) diff --git a/Source/WTF/wtf/StringExtras.h b/Source/WTF/wtf/StringExtras.h index 60644f972..6797d2ce1 100644 --- a/Source/WTF/wtf/StringExtras.h +++ b/Source/WTF/wtf/StringExtras.h @@ -36,47 +36,8 @@ #endif #if COMPILER(MSVC) -// FIXME: why a COMPILER check instead of OS? also, these should be HAVE checks -#include - -#if _MSC_VER < 1900 -inline int snprintf(char* buffer, size_t count, const char* format, ...) -{ - int result; - va_list args; - va_start(args, format); - result = _vsnprintf(buffer, count, format, args); - if (result < 0 && errno != EINVAL) - result = _vscprintf(format, args); - va_end(args); - - // In the case where the string entirely filled the buffer, _vsnprintf will not - // null-terminate it, but snprintf must. - if (count > 0) - buffer[count - 1] = '\0'; - - return result; -} -#endif - -inline double wtf_vsnprintf(char* buffer, size_t count, const char* format, va_list args) -{ - int result = _vsnprintf(buffer, count, format, args); - if (result < 0 && errno != EINVAL) - result = _vscprintf(format, args); - - // In the case where the string entirely filled the buffer, _vsnprintf will not - // null-terminate it, but vsnprintf must. - if (count > 0) - buffer[count - 1] = '\0'; - - return result; -} - -// Work around a difference in Microsoft's implementation of vsnprintf, where -// vsnprintf does not null terminate the buffer. WebKit can rely on the null termination. -#define vsnprintf(buffer, count, format, args) wtf_vsnprintf(buffer, count, format, args) +// FIXME: We should stop using these entirely and use suitable versions of equalIgnoringASCIICase instead. inline int strncasecmp(const char* s1, const char* s2, size_t len) { diff --git a/Source/WTF/wtf/qt/WorkQueueQt.cpp b/Source/WTF/wtf/qt/WorkQueueQt.cpp index be04dae3f..4e2f36409 100644 --- a/Source/WTF/wtf/qt/WorkQueueQt.cpp +++ b/Source/WTF/wtf/qt/WorkQueueQt.cpp @@ -30,7 +30,6 @@ #include #include #include -#include namespace WTF { diff --git a/Source/WebCore/page/FrameView.cpp b/Source/WebCore/page/FrameView.cpp index 2983a2d92..2cddda42c 100644 --- a/Source/WebCore/page/FrameView.cpp +++ b/Source/WebCore/page/FrameView.cpp @@ -1565,7 +1565,7 @@ void FrameView::adjustMediaTypeForPrinting(bool printing) if (printing) { if (m_mediaTypeWhenNotPrinting.isNull()) m_mediaTypeWhenNotPrinting = mediaType(); - setMediaType("print"); + setMediaType("print"); } else { if (!m_mediaTypeWhenNotPrinting.isNull()) setMediaType(m_mediaTypeWhenNotPrinting); diff --git a/Source/WebCore/platform/graphics/filters/FEConvolveMatrix.cpp b/Source/WebCore/platform/graphics/filters/FEConvolveMatrix.cpp index 9b0fe49fb..6340107aa 100644 --- a/Source/WebCore/platform/graphics/filters/FEConvolveMatrix.cpp +++ b/Source/WebCore/platform/graphics/filters/FEConvolveMatrix.cpp @@ -241,7 +241,7 @@ ALWAYS_INLINE void setDestinationPixels(Uint8ClampedArray* image, int& pixel, fl image->set(pixel++, maxAlpha); } -#if defined(_MSC_VER) && (_MSC_VER >= 1700) +#if COMPILER(MSVC) // Incorrectly diagnosing overwrite of stack in |totals| due to |preserveAlphaValues|. #pragma warning(push) #pragma warning(disable: 4789) @@ -385,7 +385,7 @@ void FEConvolveMatrix::fastSetOuterPixels(PaintingData& paintingData, int x1, in } } -#if defined(_MSC_VER) && (_MSC_VER >= 1700) +#if COMPILER(MSVC) #pragma warning(pop) // Disable of 4789 #endif diff --git a/Source/WebCore/platform/graphics/qt/FontCacheQt.cpp b/Source/WebCore/platform/graphics/qt/FontCacheQt.cpp index 1222196dd..7be647748 100644 --- a/Source/WebCore/platform/graphics/qt/FontCacheQt.cpp +++ b/Source/WebCore/platform/graphics/qt/FontCacheQt.cpp @@ -29,7 +29,6 @@ #include "FontDescription.h" #include "FontPlatformData.h" #include -#include #include #include #include diff --git a/Source/WebCore/platform/graphics/qt/FontCascadeQt.cpp b/Source/WebCore/platform/graphics/qt/FontCascadeQt.cpp index 1ead333ce..47bcd8df6 100644 --- a/Source/WebCore/platform/graphics/qt/FontCascadeQt.cpp +++ b/Source/WebCore/platform/graphics/qt/FontCascadeQt.cpp @@ -24,9 +24,7 @@ #include "Font.h" -#include "AffineTransform.h" #include "FontDescription.h" -#include "FontSelector.h" #include "GlyphBuffer.h" #include "Gradient.h" #include "GraphicsContext.h" @@ -264,8 +262,13 @@ void FontCascade::initFormatForTextLayout(QTextLayout* layout, const TextRun& ru if (isSmallCaps()) range.format.setFontCapitalization(QFont::SmallCaps); - if (range.format.propertyCount() && range.length) + if (range.format.propertyCount() && range.length) { +#if QT_VERSION >= QT_VERSION_CHECK(5, 6, 0) + layout->setFormats(QVector() << range); +#else layout->setAdditionalFormats(QList() << range); +#endif + } } bool FontCascade::canReturnFallbackFontsForComplexText() diff --git a/Source/WebCore/platform/graphics/qt/FontCustomPlatformData.h b/Source/WebCore/platform/graphics/qt/FontCustomPlatformData.h index 31d169f62..c2d0c9fa2 100644 --- a/Source/WebCore/platform/graphics/qt/FontCustomPlatformData.h +++ b/Source/WebCore/platform/graphics/qt/FontCustomPlatformData.h @@ -22,7 +22,6 @@ #ifndef FontCustomPlatformData_h #define FontCustomPlatformData_h -#include "TextFlags.h" #include #include #include diff --git a/Source/WebCore/platform/graphics/qt/FontCustomPlatformDataQt.cpp b/Source/WebCore/platform/graphics/qt/FontCustomPlatformDataQt.cpp index bc65c0511..908d881f1 100644 --- a/Source/WebCore/platform/graphics/qt/FontCustomPlatformDataQt.cpp +++ b/Source/WebCore/platform/graphics/qt/FontCustomPlatformDataQt.cpp @@ -24,7 +24,6 @@ #include "FontPlatformData.h" #include "SharedBuffer.h" -#include "WOFFFileFormat.h" #include namespace WebCore { diff --git a/Source/WebCore/platform/graphics/qt/FontPlatformData.h b/Source/WebCore/platform/graphics/qt/FontPlatformData.h index c8375ebcd..8c1327e13 100644 --- a/Source/WebCore/platform/graphics/qt/FontPlatformData.h +++ b/Source/WebCore/platform/graphics/qt/FontPlatformData.h @@ -29,7 +29,6 @@ #include #include #include -#include #include namespace WebCore { diff --git a/Source/WebCore/platform/graphics/qt/GradientQt.cpp b/Source/WebCore/platform/graphics/qt/GradientQt.cpp index 72bb00938..3412cfadd 100644 --- a/Source/WebCore/platform/graphics/qt/GradientQt.cpp +++ b/Source/WebCore/platform/graphics/qt/GradientQt.cpp @@ -27,7 +27,6 @@ #include "config.h" #include "Gradient.h" -#include "CSSParser.h" #include "GraphicsContext.h" #include diff --git a/Source/WebCore/platform/graphics/qt/GraphicsContext3DQt.cpp b/Source/WebCore/platform/graphics/qt/GraphicsContext3DQt.cpp index 7f2f07b60..fe63ff7bb 100644 --- a/Source/WebCore/platform/graphics/qt/GraphicsContext3DQt.cpp +++ b/Source/WebCore/platform/graphics/qt/GraphicsContext3DQt.cpp @@ -24,16 +24,13 @@ #include "GraphicsSurface.h" #include "HostWindow.h" #include "ImageBuffer.h" -#include "ImageData.h" #include "NativeImageQt.h" -#include "NotImplemented.h" #include "QWebPageClient.h" #include "SharedBuffer.h" #include "TextureMapperPlatformLayer.h" #include #include #include -#include #if USE(TEXTURE_MAPPER_GL) #include diff --git a/Source/WebCore/platform/graphics/qt/GraphicsContextQt.cpp b/Source/WebCore/platform/graphics/qt/GraphicsContextQt.cpp index 59519398e..260081946 100644 --- a/Source/WebCore/platform/graphics/qt/GraphicsContextQt.cpp +++ b/Source/WebCore/platform/graphics/qt/GraphicsContextQt.cpp @@ -47,10 +47,8 @@ #include "Color.h" #include "DisplayListRecorder.h" #include "FloatConversion.h" -#include "Font.h" #include "ImageBuffer.h" #include "ImageBufferDataQt.h" -#include "NotImplemented.h" #include "Path.h" #include "Pattern.h" #include "ShadowBlur.h" diff --git a/Source/WebCore/platform/graphics/qt/IconQt.cpp b/Source/WebCore/platform/graphics/qt/IconQt.cpp index 24f13067d..9bd3d5323 100644 --- a/Source/WebCore/platform/graphics/qt/IconQt.cpp +++ b/Source/WebCore/platform/graphics/qt/IconQt.cpp @@ -23,7 +23,6 @@ #include "GraphicsContext.h" #include "IntRect.h" -#include "NotImplemented.h" #include #include diff --git a/Source/WebCore/platform/graphics/qt/ImageBufferDataQt.cpp b/Source/WebCore/platform/graphics/qt/ImageBufferDataQt.cpp index e76572134..9037ae6ac 100644 --- a/Source/WebCore/platform/graphics/qt/ImageBufferDataQt.cpp +++ b/Source/WebCore/platform/graphics/qt/ImageBufferDataQt.cpp @@ -32,7 +32,6 @@ #include "GraphicsContext.h" #include "GraphicsSurface.h" -#include "ImageData.h" #include "IntRect.h" #include "StillImageQt.h" diff --git a/Source/WebCore/platform/graphics/qt/ImageBufferQt.cpp b/Source/WebCore/platform/graphics/qt/ImageBufferQt.cpp index 380d22bb5..2295362aa 100644 --- a/Source/WebCore/platform/graphics/qt/ImageBufferQt.cpp +++ b/Source/WebCore/platform/graphics/qt/ImageBufferQt.cpp @@ -31,14 +31,12 @@ #include "ImageBuffer.h" #include "GraphicsContext.h" -#include "ImageData.h" #include "IntRect.h" #include "MIMETypeRegistry.h" #include "StillImageQt.h" #include "TransparencyLayer.h" #include #include -#include #include #include diff --git a/Source/WebCore/platform/graphics/qt/MediaPlayerPrivateQt.cpp b/Source/WebCore/platform/graphics/qt/MediaPlayerPrivateQt.cpp index 95548dff3..9091fdc72 100644 --- a/Source/WebCore/platform/graphics/qt/MediaPlayerPrivateQt.cpp +++ b/Source/WebCore/platform/graphics/qt/MediaPlayerPrivateQt.cpp @@ -25,13 +25,10 @@ #include "GraphicsContext.h" #include "GraphicsLayer.h" #include "HTMLMediaElement.h" -#include "HTMLVideoElement.h" #include "Logging.h" #include "NetworkingContext.h" #include "NotImplemented.h" #include "RenderVideo.h" -#include "TimeRanges.h" -#include "Widget.h" #include #include diff --git a/Source/WebCore/platform/graphics/qt/PathQt.cpp b/Source/WebCore/platform/graphics/qt/PathQt.cpp index ecafcdb0e..f3d7481ea 100644 --- a/Source/WebCore/platform/graphics/qt/PathQt.cpp +++ b/Source/WebCore/platform/graphics/qt/PathQt.cpp @@ -34,7 +34,6 @@ #include "AffineTransform.h" #include "FloatRect.h" #include "GraphicsContext.h" -#include "ImageBuffer.h" #include "NativeImageQt.h" #include "StrokeStyleApplier.h" #include diff --git a/Source/WebCore/platform/graphics/qt/PatternQt.cpp b/Source/WebCore/platform/graphics/qt/PatternQt.cpp index 7aae62599..8795f3547 100644 --- a/Source/WebCore/platform/graphics/qt/PatternQt.cpp +++ b/Source/WebCore/platform/graphics/qt/PatternQt.cpp @@ -26,8 +26,7 @@ #include "config.h" #include "Pattern.h" -#include "AffineTransform.h" -#include "GraphicsContext.h" +#include "Image.h" namespace WebCore { diff --git a/Source/WebCore/platform/graphics/qt/StillImageQt.cpp b/Source/WebCore/platform/graphics/qt/StillImageQt.cpp index 5569474f0..a2fc59e9f 100644 --- a/Source/WebCore/platform/graphics/qt/StillImageQt.cpp +++ b/Source/WebCore/platform/graphics/qt/StillImageQt.cpp @@ -29,7 +29,6 @@ #include "StillImageQt.h" #include "GraphicsContext.h" -#include "IntSize.h" #include "ShadowBlur.h" #include diff --git a/Source/WebCore/platform/graphics/qt/TransformationMatrixQt.cpp b/Source/WebCore/platform/graphics/qt/TransformationMatrixQt.cpp index 73a0e414f..bf3e8c6c5 100644 --- a/Source/WebCore/platform/graphics/qt/TransformationMatrixQt.cpp +++ b/Source/WebCore/platform/graphics/qt/TransformationMatrixQt.cpp @@ -27,8 +27,6 @@ #include "AffineTransform.h" #include "TransformationMatrix.h" -#include "FloatRect.h" -#include "IntRect.h" namespace WebCore { diff --git a/Source/WebCore/platform/network/qt/ResourceHandleQt.cpp b/Source/WebCore/platform/network/qt/ResourceHandleQt.cpp index b850e2327..8b69383ff 100644 --- a/Source/WebCore/platform/network/qt/ResourceHandleQt.cpp +++ b/Source/WebCore/platform/network/qt/ResourceHandleQt.cpp @@ -30,10 +30,6 @@ #include "config.h" #include "ResourceHandle.h" -#include "CachedResourceLoader.h" -#include "Frame.h" -#include "FrameNetworkingContext.h" -#include "NotImplemented.h" #include "Page.h" #include "QNetworkReplyHandler.h" #include "ResourceHandleClient.h" diff --git a/Source/WebCore/platform/network/qt/ResourceRequestQt.cpp b/Source/WebCore/platform/network/qt/ResourceRequestQt.cpp index d74073ec5..655724a4c 100644 --- a/Source/WebCore/platform/network/qt/ResourceRequestQt.cpp +++ b/Source/WebCore/platform/network/qt/ResourceRequestQt.cpp @@ -101,6 +101,12 @@ QNetworkRequest ResourceRequest::toNetworkRequest(NetworkingContext *context) co request.setUrl(newurl); request.setOriginatingObject(context ? context->originatingObject() : 0); +#if QT_VERSION >= QT_VERSION_CHECK(5, 8, 0) + // HTTP2AllowedAttribute enforces HTTP/2 instead of negotiating, see QTBUG-61397 + if (newurl.scheme().toLower() == QLatin1String("https")) + request.setAttribute(QNetworkRequest::HTTP2AllowedAttribute, true); +#endif + const HTTPHeaderMap &headers = httpHeaderFields(); for (HTTPHeaderMap::const_iterator it = headers.begin(), end = headers.end(); it != end; ++it) { diff --git a/Source/WebCore/platform/qt/DeviceMotionClientQt.cpp b/Source/WebCore/platform/qt/DeviceMotionClientQt.cpp index 88fb5c1c6..5c01f29f5 100644 --- a/Source/WebCore/platform/qt/DeviceMotionClientQt.cpp +++ b/Source/WebCore/platform/qt/DeviceMotionClientQt.cpp @@ -23,7 +23,6 @@ #include "DeviceMotionProviderQt.h" -#include namespace WebCore { diff --git a/Source/WebCore/platform/qt/GamepadsQt.cpp b/Source/WebCore/platform/qt/GamepadsQt.cpp index 6fff52f9a..70b4305de 100644 --- a/Source/WebCore/platform/qt/GamepadsQt.cpp +++ b/Source/WebCore/platform/qt/GamepadsQt.cpp @@ -37,7 +37,6 @@ #include #include #include -#include #include // Forward declarations for libudev, they are all used opaque so we don't need the definitions. diff --git a/Source/WebCore/platform/qt/MIMETypeRegistryQt.cpp b/Source/WebCore/platform/qt/MIMETypeRegistryQt.cpp index 3e3f879ed..ab34c8333 100644 --- a/Source/WebCore/platform/qt/MIMETypeRegistryQt.cpp +++ b/Source/WebCore/platform/qt/MIMETypeRegistryQt.cpp @@ -31,7 +31,6 @@ #include #include -#include namespace WebCore { diff --git a/Source/WebCore/platform/qt/MainThreadSharedTimerQt.cpp b/Source/WebCore/platform/qt/MainThreadSharedTimerQt.cpp index 7aae3f1de..0f0864106 100644 --- a/Source/WebCore/platform/qt/MainThreadSharedTimerQt.cpp +++ b/Source/WebCore/platform/qt/MainThreadSharedTimerQt.cpp @@ -34,7 +34,6 @@ #include #include #include -#include namespace WebCore { diff --git a/Source/WebCore/platform/qt/PlatformGestureEvent.h b/Source/WebCore/platform/qt/PlatformGestureEvent.h index 1beac6a68..1a0006842 100644 --- a/Source/WebCore/platform/qt/PlatformGestureEvent.h +++ b/Source/WebCore/platform/qt/PlatformGestureEvent.h @@ -28,7 +28,6 @@ #if ENABLE(QT_GESTURE_EVENTS) -#include "FloatPoint.h" #include "IntPoint.h" #include "IntSize.h" #include "PlatformEvent.h" diff --git a/Source/WebCore/platform/qt/PlatformScreenQt.cpp b/Source/WebCore/platform/qt/PlatformScreenQt.cpp index 91ff0ab43..2790a0d9c 100644 --- a/Source/WebCore/platform/qt/PlatformScreenQt.cpp +++ b/Source/WebCore/platform/qt/PlatformScreenQt.cpp @@ -32,7 +32,6 @@ #include "PlatformScreen.h" #include "FloatRect.h" -#include "Frame.h" #include "FrameView.h" #include "HostWindow.h" #include "NotImplemented.h" diff --git a/Source/WebCore/platform/qt/RenderThemeQStyle.cpp b/Source/WebCore/platform/qt/RenderThemeQStyle.cpp index 7373acca7..706570399 100644 --- a/Source/WebCore/platform/qt/RenderThemeQStyle.cpp +++ b/Source/WebCore/platform/qt/RenderThemeQStyle.cpp @@ -34,23 +34,17 @@ #include "CSSValueKeywords.h" #include "Chrome.h" #include "ChromeClient.h" -#include "Color.h" #include "Document.h" -#include "Font.h" -#include "FontSelector.h" #include "GraphicsContext.h" #include "HTMLInputElement.h" #include "HTMLNames.h" -#include "LocalizedStrings.h" #include "NotImplemented.h" #include "Page.h" #include "PaintInfo.h" #include "QWebPageClient.h" #include "RenderBox.h" #include "RenderProgress.h" -#include "RenderSlider.h" #include "ScrollbarThemeQStyle.h" -#include "SliderThumbElement.h" #include "StyleResolver.h" #include "UserAgentStyleSheets.h" diff --git a/Source/WebCore/platform/qt/RenderThemeQt.cpp b/Source/WebCore/platform/qt/RenderThemeQt.cpp index 2cd35700a..01968deba 100644 --- a/Source/WebCore/platform/qt/RenderThemeQt.cpp +++ b/Source/WebCore/platform/qt/RenderThemeQt.cpp @@ -31,21 +31,15 @@ #include "RenderThemeQt.h" #include "CSSValueKeywords.h" -#include "Chrome.h" #include "ChromeClient.h" #include "Color.h" #include "ExceptionCodePlaceholder.h" #include "FileList.h" -#include "Font.h" -#include "FontSelector.h" #include "GraphicsContext.h" #include "HTMLInputElement.h" #include "HTMLMediaElement.h" #include "HTMLNames.h" #include "LocalizedStrings.h" -#if ENABLE(VIDEO) -#include "MediaControlElements.h" -#endif #include "NotImplemented.h" #include "Page.h" #include "PaintInfo.h" @@ -56,9 +50,6 @@ #include "ScrollbarTheme.h" #include "StyleResolver.h" #include "TimeRanges.h" -#if ENABLE(VIDEO) -#include "UserAgentScripts.h" -#endif #include "UserAgentStyleSheets.h" #include @@ -69,6 +60,10 @@ #include +#if ENABLE(VIDEO) +#include "UserAgentScripts.h" +#endif + namespace WebCore { using namespace HTMLNames; @@ -542,7 +537,7 @@ bool RenderThemeQt::supportsFocus(ControlPart appearance) const #if ENABLE(VIDEO) String RenderThemeQt::mediaControlsStyleSheet() { - return ASCIILiteral(mediaControlsBaseUserAgentStyleSheet); + return String(mediaControlsBaseUserAgentStyleSheet, sizeof(mediaControlsBaseUserAgentStyleSheet)); } String RenderThemeQt::mediaControlsScript() diff --git a/Source/WebCore/platform/qt/RenderThemeQtMobile.cpp b/Source/WebCore/platform/qt/RenderThemeQtMobile.cpp index e4a34de29..cf5f6491b 100644 --- a/Source/WebCore/platform/qt/RenderThemeQtMobile.cpp +++ b/Source/WebCore/platform/qt/RenderThemeQtMobile.cpp @@ -30,11 +30,8 @@ #include "HTMLInputElement.h" #include "HTMLNames.h" #include "HTMLSelectElement.h" -#include "LocalizedStrings.h" -#include "NotImplemented.h" #include "Page.h" #include "PaintInfo.h" -#include "QWebPageClient.h" #include "RenderBox.h" #include "RenderProgress.h" #include "StyleResolver.h" diff --git a/Source/WebCore/platform/qt/TemporaryLinkStubsQt.cpp b/Source/WebCore/platform/qt/TemporaryLinkStubsQt.cpp index fb3352675..1ccc38a67 100644 --- a/Source/WebCore/platform/qt/TemporaryLinkStubsQt.cpp +++ b/Source/WebCore/platform/qt/TemporaryLinkStubsQt.cpp @@ -32,42 +32,17 @@ #include "config.h" -#include "AXObjectCache.h" -#include "CachedResource.h" -#include "CookieJar.h" #include "CookieStorage.h" -#include "Cursor.h" -#include "DNS.h" -#include "FTPDirectoryDocument.h" -#include "FileSystem.h" -#include "Font.h" -#include "Frame.h" -#include "FrameLoader.h" -#include "FrameView.h" -#include "GraphicsContext.h" -#include "IconLoader.h" -#include "IntPoint.h" -#include "URL.h" -#include "Language.h" -#include "LocalizedStrings.h" -#include "Node.h" #include "NotImplemented.h" -#include "Path.h" -#include "PlatformMouseEvent.h" -#include "RenderTheme.h" -#include "SharedBuffer.h" -#include "TextBoundaries.h" -#include "Widget.h" - -#include -#include -#include -#include +#include +#include using namespace WebCore; namespace WebCore { +class URL; + void getSupportedKeySizes(Vector&) { notImplemented(); diff --git a/Source/WebCore/platform/qt/ThirdPartyCookiesQt.cpp b/Source/WebCore/platform/qt/ThirdPartyCookiesQt.cpp index 3f2f572ad..4bfb7244f 100644 --- a/Source/WebCore/platform/qt/ThirdPartyCookiesQt.cpp +++ b/Source/WebCore/platform/qt/ThirdPartyCookiesQt.cpp @@ -20,8 +20,6 @@ #include "config.h" #include "ThirdPartyCookiesQt.h" -#include "Cookie.h" -#include "CookieJar.h" #include "Document.h" #include "NetworkingContext.h" diff --git a/Source/WebCore/platform/qt/URLQt.cpp b/Source/WebCore/platform/qt/URLQt.cpp index 7b588fa5b..00ab8e7ab 100644 --- a/Source/WebCore/platform/qt/URLQt.cpp +++ b/Source/WebCore/platform/qt/URLQt.cpp @@ -20,10 +20,8 @@ #include "config.h" #include "URL.h" -#include "NotImplemented.h" #include "TextEncoding.h" #include "qurl.h" -#include namespace WebCore { diff --git a/Source/WebCore/platform/qt/WidgetQt.cpp b/Source/WebCore/platform/qt/WidgetQt.cpp index 0d1669941..715ed09ea 100644 --- a/Source/WebCore/platform/qt/WidgetQt.cpp +++ b/Source/WebCore/platform/qt/WidgetQt.cpp @@ -33,7 +33,6 @@ #include "Widget.h" #include "Cursor.h" -#include "Font.h" #include "GraphicsContext.h" #include "HostWindow.h" #include "IntRect.h" diff --git a/Source/WebCore/xml/XSLTUnicodeSort.cpp b/Source/WebCore/xml/XSLTUnicodeSort.cpp index 54d5abd10..def0f9482 100644 --- a/Source/WebCore/xml/XSLTUnicodeSort.cpp +++ b/Source/WebCore/xml/XSLTUnicodeSort.cpp @@ -33,6 +33,8 @@ #include #include +#include +#include #include #if OS(DARWIN) && !PLATFORM(EFL) && !PLATFORM(GTK) && !PLATFORM(QT) @@ -51,15 +53,19 @@ void xsltTransformErrorTrampoline(xsltTransformContextPtr context, xsltStyleshee { va_list args; va_start(args, message); - char* messageWithArgs; - vasprintf(&messageWithArgs, message, args); + + va_list preflightArgs; + va_copy(preflightArgs, args); + size_t stringLength = vsnprintf(nullptr, 0, message, preflightArgs); + va_end(preflightArgs); + + Vector buffer(stringLength + 1); + vsnprintf(buffer.data(), stringLength + 1, message, args); va_end(args); static void (*xsltTransformErrorPointer)(xsltTransformContextPtr, xsltStylesheetPtr, xmlNodePtr, const char*, ...) WTF_ATTRIBUTE_PRINTF(4, 5) = reinterpret_cast(dlsym(libxsltLibrary(), "xsltTransformError")); - xsltTransformErrorPointer(context, style, node, "%s", messageWithArgs); - - free(messageWithArgs); + xsltTransformErrorPointer(context, style, node, "%s", buffer.data()); } #define xsltTransformError xsltTransformErrorTrampoline diff --git a/Source/WebCore/xml/parser/XMLDocumentParserLibxml2.cpp b/Source/WebCore/xml/parser/XMLDocumentParserLibxml2.cpp index 0e77eac4d..0bcdc4c92 100644 --- a/Source/WebCore/xml/parser/XMLDocumentParserLibxml2.cpp +++ b/Source/WebCore/xml/parser/XMLDocumentParserLibxml2.cpp @@ -963,24 +963,19 @@ void XMLDocumentParser::error(XMLErrors::ErrorType type, const char* message, va if (isStopped()) return; -#if HAVE(VASPRINTF) - char* m; - if (vasprintf(&m, message, args) == -1) - return; -#else - char m[1024]; - vsnprintf(m, sizeof(m) - 1, message, args); -#endif + va_list preflightArgs; + va_copy(preflightArgs, args); + size_t stringLength = vsnprintf(nullptr, 0, message, preflightArgs); + va_end(preflightArgs); + + Vector buffer(stringLength + 1); + vsnprintf(buffer.data(), stringLength + 1, message, args); TextPosition position = textPosition(); if (m_parserPaused) - m_pendingCallbacks->appendErrorCallback(type, reinterpret_cast(m), position.m_line, position.m_column); + m_pendingCallbacks->appendErrorCallback(type, reinterpret_cast(buffer.data()), position.m_line, position.m_column); else - handleError(type, m, textPosition()); - -#if HAVE(VASPRINTF) - free(m); -#endif + handleError(type, buffer.data(), textPosition()); } void XMLDocumentParser::processingInstruction(const xmlChar* target, const xmlChar* data) diff --git a/Source/WebKit/CMakeLists.txt b/Source/WebKit/CMakeLists.txt index edc22fee9..82dc1e662 100644 --- a/Source/WebKit/CMakeLists.txt +++ b/Source/WebKit/CMakeLists.txt @@ -60,7 +60,7 @@ if (${PORT} STREQUAL "Qt") DESTINATION "${LIB_INSTALL_DIR}" RUNTIME DESTINATION "${BIN_INSTALL_DIR}" ) - if (MSVC) + if (MSVC AND NOT QT_STATIC_BUILD) install(FILES $ DESTINATION "${BIN_INSTALL_DIR}" OPTIONAL) endif () diff --git a/Source/WebKit/PlatformQt.cmake b/Source/WebKit/PlatformQt.cmake index da199aeaf..3e50b2552 100644 --- a/Source/WebKit/PlatformQt.cmake +++ b/Source/WebKit/PlatformQt.cmake @@ -758,7 +758,7 @@ install(TARGETS WebKitWidgets EXPORT Qt5WebKitWidgetsTargets DESTINATION "${LIB_INSTALL_DIR}" RUNTIME DESTINATION "${BIN_INSTALL_DIR}" ) -if (MSVC) +if (MSVC AND NOT QT_STATIC_BUILD) install(FILES $ DESTINATION "${BIN_INSTALL_DIR}" OPTIONAL) endif () diff --git a/Source/WebKit2/CMakeLists.txt b/Source/WebKit2/CMakeLists.txt index e5d08ed68..aa7863cbd 100644 --- a/Source/WebKit2/CMakeLists.txt +++ b/Source/WebKit2/CMakeLists.txt @@ -1,3 +1,6 @@ +include(CheckCXXSourceCompiles) +include(CheckFunctionExists) + set(WebKit2_INCLUDE_DIRECTORIES "${JAVASCRIPTCORE_DIR}/llint" "${WEBKIT2_DIR}" @@ -740,11 +743,33 @@ set(PluginProcess_LIBRARIES WebKit2 ) -# librt is needed for shm_open on Linux. -find_library(LIBRT_LIBRARIES NAMES rt) -mark_as_advanced(LIBRT_LIBRARIES) -if (LIBRT_LIBRARIES) - list(APPEND WebKit2_LIBRARIES ${LIBRT_LIBRARIES}) +if (COMPILER_IS_GCC_OR_CLANG) + set(ATOMIC_TEST_SOURCE + " + #include + int main() { std::atomic i(0); i++; return 0; } + " + ) + check_cxx_source_compiles("${ATOMIC_TEST_SOURCE}" ATOMIC_INT64_IS_BUILTIN) + if (NOT ATOMIC_INT64_IS_BUILTIN) + set(CMAKE_REQUIRED_LIBRARIES atomic) + check_cxx_source_compiles("${ATOMIC_TEST_SOURCE}" ATOMIC_INT64_REQUIRES_LIBATOMIC) + if (ATOMIC_INT64_REQUIRES_LIBATOMIC) + list(APPEND WebKit2_LIBRARIES atomic) + endif () + unset(CMAKE_REQUIRED_LIBRARIES) + endif () +endif () + +if (UNIX) + check_function_exists(shm_open SHM_OPEN_EXISTS) + if (NOT SHM_OPEN_EXISTS) + set(CMAKE_REQUIRED_LIBRARIES rt) + check_function_exists(shm_open SHM_OPEN_REQUIRES_LIBRT) + if (SHM_OPEN_REQUIRES_LIBRT) + list(APPEND WebKit2_LIBRARIES rt) + endif () + endif () endif () macro(ADD_WEBKIT2_PREFIX_HEADER _target) diff --git a/Source/WebKit2/NetworkProcess/qt/NetworkProcessQt.cpp b/Source/WebKit2/NetworkProcess/qt/NetworkProcessQt.cpp index f822b3d20..2fc32f302 100644 --- a/Source/WebKit2/NetworkProcess/qt/NetworkProcessQt.cpp +++ b/Source/WebKit2/NetworkProcess/qt/NetworkProcessQt.cpp @@ -27,7 +27,6 @@ #include "NetworkProcess.h" #include "NetworkProcessCreationParameters.h" -#include "QtNetworkAccessManager.h" #include #include diff --git a/Source/WebKit2/NetworkProcess/qt/RemoteNetworkingContextQt.cpp b/Source/WebKit2/NetworkProcess/qt/RemoteNetworkingContextQt.cpp index 96da15886..bffc35074 100644 --- a/Source/WebKit2/NetworkProcess/qt/RemoteNetworkingContextQt.cpp +++ b/Source/WebKit2/NetworkProcess/qt/RemoteNetworkingContextQt.cpp @@ -32,7 +32,6 @@ #include #include #include -#include using namespace WebCore; diff --git a/Source/WebKit2/Platform/IPC/win/ConnectionWin.cpp b/Source/WebKit2/Platform/IPC/win/ConnectionWin.cpp index 7ea5ba0f5..c5a8ccfa9 100644 --- a/Source/WebKit2/Platform/IPC/win/ConnectionWin.cpp +++ b/Source/WebKit2/Platform/IPC/win/ConnectionWin.cpp @@ -29,6 +29,7 @@ #include "DataReference.h" #include #include +#include #include using namespace std; @@ -46,7 +47,7 @@ bool Connection::createServerAndClientIdentifiers(HANDLE& serverIdentifier, HAND unsigned uniqueID = randomNumber() * std::numeric_limits::max(); pipeName = String::format("\\\\.\\pipe\\com.apple.WebKit.%x", uniqueID); - serverIdentifier = ::CreateNamedPipe(pipeName.charactersWithNullTermination().data(), + serverIdentifier = ::CreateNamedPipe(stringToNullTerminatedWChar(pipeName).data(), PIPE_ACCESS_DUPLEX | FILE_FLAG_FIRST_PIPE_INSTANCE | FILE_FLAG_OVERLAPPED, PIPE_TYPE_MESSAGE | PIPE_READMODE_MESSAGE, 1, inlineMessageMaxSize, inlineMessageMaxSize, 0, 0); @@ -61,7 +62,7 @@ bool Connection::createServerAndClientIdentifiers(HANDLE& serverIdentifier, HAND if (!serverIdentifier) return false; - clientIdentifier = ::CreateFileW(pipeName.charactersWithNullTermination().data(), GENERIC_READ | GENERIC_WRITE, 0, 0, OPEN_EXISTING, FILE_FLAG_OVERLAPPED, 0); + clientIdentifier = ::CreateFileW(stringToNullTerminatedWChar(pipeName).data(), GENERIC_READ | GENERIC_WRITE, 0, 0, OPEN_EXISTING, FILE_FLAG_OVERLAPPED, 0); if (!clientIdentifier) { ::CloseHandle(serverIdentifier); return false; diff --git a/Source/WebKit2/PluginProcess/qt/PluginControllerProxyQt.cpp b/Source/WebKit2/PluginProcess/qt/PluginControllerProxyQt.cpp index 743adfaa4..75a7544e5 100644 --- a/Source/WebKit2/PluginProcess/qt/PluginControllerProxyQt.cpp +++ b/Source/WebKit2/PluginProcess/qt/PluginControllerProxyQt.cpp @@ -28,7 +28,6 @@ #if ENABLE(PLUGIN_PROCESS) -#include "PluginProcess.h" #include using namespace WebCore; diff --git a/Source/WebKit2/PluginProcess/qt/PluginProcessQt.cpp b/Source/WebKit2/PluginProcess/qt/PluginProcessQt.cpp index b584f73c0..93e16e090 100644 --- a/Source/WebKit2/PluginProcess/qt/PluginProcessQt.cpp +++ b/Source/WebKit2/PluginProcess/qt/PluginProcessQt.cpp @@ -28,7 +28,6 @@ #if ENABLE(PLUGIN_PROCESS) -#include "NetscapePlugin.h" #include "PluginProcessCreationParameters.h" #include diff --git a/Source/WebKit2/Shared/qt/ArgumentCodersQt.cpp b/Source/WebKit2/Shared/qt/ArgumentCodersQt.cpp index 766568519..511c4eaca 100644 --- a/Source/WebKit2/Shared/qt/ArgumentCodersQt.cpp +++ b/Source/WebKit2/Shared/qt/ArgumentCodersQt.cpp @@ -20,7 +20,6 @@ #include "config.h" #include "ArgumentCodersQt.h" -#include "ArgumentCoders.h" #include "WebCoreArgumentCoders.h" #include #include diff --git a/Source/WebKit2/Shared/qt/WebEventFactoryQt.cpp b/Source/WebKit2/Shared/qt/WebEventFactoryQt.cpp index 876208b99..50fcb5ccd 100644 --- a/Source/WebKit2/Shared/qt/WebEventFactoryQt.cpp +++ b/Source/WebKit2/Shared/qt/WebEventFactoryQt.cpp @@ -34,7 +34,6 @@ #include #include #include -#include #include using namespace WebCore; diff --git a/Source/WebKit2/UIProcess/API/cpp/qt/WKStringQt.cpp b/Source/WebKit2/UIProcess/API/cpp/qt/WKStringQt.cpp index 6fad021f6..8532cae3e 100644 --- a/Source/WebKit2/UIProcess/API/cpp/qt/WKStringQt.cpp +++ b/Source/WebKit2/UIProcess/API/cpp/qt/WKStringQt.cpp @@ -24,7 +24,6 @@ #include "WKAPICast.h" #include "WKRetainPtr.h" #include -#include #include using namespace WebKit; diff --git a/Source/WebKit2/UIProcess/API/cpp/qt/WKURLQt.cpp b/Source/WebKit2/UIProcess/API/cpp/qt/WKURLQt.cpp index f9177fd59..3f5396a4b 100644 --- a/Source/WebKit2/UIProcess/API/cpp/qt/WKURLQt.cpp +++ b/Source/WebKit2/UIProcess/API/cpp/qt/WKURLQt.cpp @@ -21,10 +21,9 @@ #include "config.h" #include "WKURLQt.h" -#include "WKAPICast.h" #include "WKRetainPtr.h" +#include "WKSharedAPICast.h" #include -#include #include using namespace WebKit; diff --git a/Source/WebKit2/UIProcess/API/qt/qquicknetworkreply_p.h b/Source/WebKit2/UIProcess/API/qt/qquicknetworkreply_p.h index 453e766b0..0ea65b9d7 100644 --- a/Source/WebKit2/UIProcess/API/qt/qquicknetworkreply_p.h +++ b/Source/WebKit2/UIProcess/API/qt/qquicknetworkreply_p.h @@ -23,7 +23,6 @@ #include "QtNetworkReplyData.h" #include "QtNetworkRequestData.h" -#include "SharedMemory.h" #include "qquickwebview_p.h" #include "qwebkitglobal.h" #include diff --git a/Source/WebKit2/UIProcess/API/qt/qquickwebpage.cpp b/Source/WebKit2/UIProcess/API/qt/qquickwebpage.cpp index f6717a405..f2c2cb5a7 100644 --- a/Source/WebKit2/UIProcess/API/qt/qquickwebpage.cpp +++ b/Source/WebKit2/UIProcess/API/qt/qquickwebpage.cpp @@ -22,9 +22,7 @@ #include "qquickwebpage_p.h" #include "CoordinatedGraphicsScene.h" -#include "QtWebPageEventHandler.h" #include "QtWebPageSGNode.h" -#include "TransformationMatrix.h" #include "qquickwebpage_p_p.h" #include "qquickwebview_p.h" #include "qquickwebview_p_p.h" diff --git a/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp b/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp index cf8ac19d9..3b84c6dba 100644 --- a/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp +++ b/Source/WebKit2/UIProcess/API/qt/qquickwebview.cpp @@ -38,7 +38,6 @@ #include "QtWebPageEventHandler.h" #include "QtWebPagePolicyClient.h" #include "WebBackForwardList.h" -#include "WebFindOptions.h" #if ENABLE(INSPECTOR_SERVER) #include "WebInspectorProxy.h" #include "WebInspectorServer.h" @@ -75,7 +74,6 @@ #include #include #include -#include #include #include #include diff --git a/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h b/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h index fe40823ea..cca489582 100644 --- a/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h +++ b/Source/WebKit2/UIProcess/API/qt/qquickwebview_p_p.h @@ -23,7 +23,6 @@ #include "DefaultUndoController.h" #include "PageViewportController.h" -#include "PageViewportControllerClient.h" #include "QtPageClient.h" #include "QtWebPageUIClient.h" diff --git a/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory.cpp b/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory.cpp index fa8982c4f..f12d2b105 100644 --- a/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory.cpp +++ b/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory.cpp @@ -28,7 +28,6 @@ #include "WKBackForwardListRef.h" #include "WKStringQt.h" -#include "WKURL.h" #include "WKURLQt.h" #include "qwebnavigationhistory_p_p.h" diff --git a/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory_p_p.h b/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory_p_p.h index 527aa4658..e3fd6ca92 100644 --- a/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory_p_p.h +++ b/Source/WebKit2/UIProcess/API/qt/qwebnavigationhistory_p_p.h @@ -31,7 +31,6 @@ #include #include #include -#include namespace WebKit { class WebBackForwardList; diff --git a/Source/WebKit2/UIProcess/API/qt/qwebpreferences.cpp b/Source/WebKit2/UIProcess/API/qt/qwebpreferences.cpp index cead3f7c2..a056173e8 100644 --- a/Source/WebKit2/UIProcess/API/qt/qwebpreferences.cpp +++ b/Source/WebKit2/UIProcess/API/qt/qwebpreferences.cpp @@ -23,8 +23,6 @@ #include "WebPageGroup.h" #include "qquickwebview_p_p.h" #include "qwebpreferences_p_p.h" -#include -#include #include #include #include diff --git a/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp b/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp index 6b6bcf5c6..53913fa56 100644 --- a/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp +++ b/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp @@ -36,16 +36,12 @@ #include #include #include -#include -#include #include -#include #include #if defined(Q_OS_UNIX) #include #include -#include #include #include #include diff --git a/Source/WebKit2/UIProcess/qt/PageViewportControllerClientQt.cpp b/Source/WebKit2/UIProcess/qt/PageViewportControllerClientQt.cpp index adac7bb80..fe301c9ab 100644 --- a/Source/WebKit2/UIProcess/qt/PageViewportControllerClientQt.cpp +++ b/Source/WebKit2/UIProcess/qt/PageViewportControllerClientQt.cpp @@ -30,7 +30,6 @@ #include #include #include -#include #include #include diff --git a/Source/WebKit2/UIProcess/qt/QtWebContext.cpp b/Source/WebKit2/UIProcess/qt/QtWebContext.cpp index 7030e13d9..7f4d46de2 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebContext.cpp +++ b/Source/WebKit2/UIProcess/qt/QtWebContext.cpp @@ -28,7 +28,6 @@ #include #include #include -#include #include #include #include diff --git a/Source/WebKit2/UIProcess/qt/QtWebContext.h b/Source/WebKit2/UIProcess/qt/QtWebContext.h index 972e388a4..93540c078 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebContext.h +++ b/Source/WebKit2/UIProcess/qt/QtWebContext.h @@ -23,7 +23,6 @@ #include #include -#include #include namespace WebKit { diff --git a/Source/WebKit2/UIProcess/qt/QtWebError.cpp b/Source/WebKit2/UIProcess/qt/QtWebError.cpp index 940e2a510..357b5e1f8 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebError.cpp +++ b/Source/WebKit2/UIProcess/qt/QtWebError.cpp @@ -25,10 +25,7 @@ #include #include -#include #include -#include -#include #include namespace WebKit { diff --git a/Source/WebKit2/UIProcess/qt/QtWebPagePolicyClient.cpp b/Source/WebKit2/UIProcess/qt/QtWebPagePolicyClient.cpp index 90e74fd9c..e32d784a5 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebPagePolicyClient.cpp +++ b/Source/WebKit2/UIProcess/qt/QtWebPagePolicyClient.cpp @@ -22,13 +22,15 @@ #include "QtWebPagePolicyClient.h" #include "WKFrame.h" +#include "WKPagePolicyClient.h" +#include "WKSharedAPICast.h" #include "WKURLQt.h" -#include "qquickwebview_p_p.h" #include "qwebnavigationrequest_p.h" #include #include #include #include +#include namespace WebKit { diff --git a/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.cpp b/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.cpp index c58f20065..7573063ac 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.cpp +++ b/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.cpp @@ -29,7 +29,6 @@ #include #include #include -#include #include namespace WebKit { diff --git a/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.h b/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.h index b608d5880..469682591 100644 --- a/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.h +++ b/Source/WebKit2/UIProcess/qt/QtWebPageUIClient.h @@ -24,9 +24,7 @@ #include #include #include -#include #include -#include class QQuickWebView; class QWebPermissionRequest; diff --git a/Source/WebKit2/UIProcess/qt/WebFullScreenManagerProxyQt.cpp b/Source/WebKit2/UIProcess/qt/WebFullScreenManagerProxyQt.cpp index 7d19da5d2..2b97dc722 100644 --- a/Source/WebKit2/UIProcess/qt/WebFullScreenManagerProxyQt.cpp +++ b/Source/WebKit2/UIProcess/qt/WebFullScreenManagerProxyQt.cpp @@ -25,7 +25,6 @@ #include "WebContext.h" #include "WebFullScreenManagerMessages.h" #include "WebFullScreenManagerProxyMessages.h" -#include "WebProcess.h" #include #if HAVE(QTQUICK) diff --git a/Source/WebKit2/UIProcess/qt/WebProcessPoolQt.cpp b/Source/WebKit2/UIProcess/qt/WebProcessPoolQt.cpp index e2662a7d7..520ea73d9 100644 --- a/Source/WebKit2/UIProcess/qt/WebProcessPoolQt.cpp +++ b/Source/WebKit2/UIProcess/qt/WebProcessPoolQt.cpp @@ -30,7 +30,6 @@ #include "NetworkProcessCreationParameters.h" #include "QtWebContext.h" #include "WKSharedAPICast.h" -#include "WebCookieManagerProxy.h" #include "WebProcessCreationParameters.h" #include #include diff --git a/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp b/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp index 8b93b2903..27ad4e30a 100644 --- a/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp +++ b/Source/WebKit2/WebProcess/WebCoreSupport/qt/WebDragClientQt.cpp @@ -33,7 +33,6 @@ #include "GraphicsContext.h" #include "Pasteboard.h" #include "ShareableBitmap.h" -#include "WebCoreArgumentCoders.h" #include "WebPage.h" #include "WebPageProxyMessages.h" diff --git a/Source/WebKit2/WebProcess/WebPage/qt/WebPageQt.cpp b/Source/WebKit2/WebProcess/WebPage/qt/WebPageQt.cpp index 899d09a51..5dd083c7c 100644 --- a/Source/WebKit2/WebProcess/WebPage/qt/WebPageQt.cpp +++ b/Source/WebKit2/WebProcess/WebPage/qt/WebPageQt.cpp @@ -29,11 +29,9 @@ #include "NotImplemented.h" #include "PopupMenuClient.h" -#include "WebEditorClient.h" #include "WebEvent.h" #include "WebPageProxyMessages.h" #include "WebPopupMenu.h" -#include "WebProcess.h" #include #include #include diff --git a/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.cpp b/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.cpp index ae2c96fbb..2ab8adf46 100644 --- a/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.cpp +++ b/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.cpp @@ -28,11 +28,9 @@ #include "QtBuiltinBundle.h" #include "QtBuiltinBundlePage.h" -#include "WKBundlePage.h" #include "WKData.h" #include "WKNumber.h" #include "WKString.h" -#include "WKStringQt.h" #include "WKType.h" namespace WebKit { diff --git a/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.h b/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.h index bf4b6c45a..b79ad418b 100644 --- a/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.h +++ b/Source/WebKit2/WebProcess/qt/QtBuiltinBundle.h @@ -28,7 +28,6 @@ #define QtBuiltinBundle_h #include "WKBundle.h" -#include "WKBundlePage.h" #include namespace WebKit { diff --git a/Source/WebKit2/WebProcess/qt/QtBuiltinBundlePage.cpp b/Source/WebKit2/WebProcess/qt/QtBuiltinBundlePage.cpp index fa368a962..92a034e89 100644 --- a/Source/WebKit2/WebProcess/qt/QtBuiltinBundlePage.cpp +++ b/Source/WebKit2/WebProcess/qt/QtBuiltinBundlePage.cpp @@ -35,8 +35,6 @@ #include "WKRetainPtr.h" #include "WKString.h" #include "WKStringPrivate.h" -#include "WKStringQt.h" -#include #include #include #include diff --git a/Source/cmake/ECMEnableSanitizers.cmake b/Source/cmake/ECMEnableSanitizers.cmake new file mode 100644 index 000000000..06cc0b66d --- /dev/null +++ b/Source/cmake/ECMEnableSanitizers.cmake @@ -0,0 +1,173 @@ +#.rst: +# ECMEnableSanitizers +# ------------------- +# +# Enable compiler sanitizer flags. +# +# The following sanitizers are supported: +# +# - Address Sanitizer +# - Memory Sanitizer +# - Thread Sanitizer +# - Leak Sanitizer +# - Undefined Behaviour Sanitizer +# +# All of them are implemented in Clang, depending on your version, and +# there is an work in progress in GCC, where some of them are currently +# implemented. +# +# This module will check your current compiler version to see if it +# supports the sanitizers that you want to enable +# +# Usage +# ===== +# +# Simply add:: +# +# include(ECMEnableSanitizers) +# +# to your ``CMakeLists.txt``. Note that this module is included in +# KDECompilerSettings, so projects using that module do not need to also +# include this one. +# +# The sanitizers are not enabled by default. Instead, you must set +# ``ECM_ENABLE_SANITIZERS`` (either in your ``CMakeLists.txt`` or on the +# command line) to a semicolon-separated list of sanitizers you wish to enable. +# The options are: +# +# - address +# - memory +# - thread +# - leak +# - undefined +# +# The sanitizers "address", "memory" and "thread" are mutually exclusive. You +# cannot enable two of them in the same build. +# +# "leak" requires the "address" sanitizer. +# +# .. note:: +# +# To reduce the overhead induced by the instrumentation of the sanitizers, it +# is advised to enable compiler optimizations (``-O1`` or higher). +# +# Example +# ======= +# +# This is an example of usage:: +# +# mkdir build +# cd build +# cmake -DECM_ENABLE_SANITIZERS='address;leak;undefined' .. +# +# .. note:: +# +# Most of the sanitizers will require Clang. To enable it, use:: +# +# -DCMAKE_CXX_COMPILER=clang++ +# +# Since 1.3.0. + +#============================================================================= +# Copyright 2014 Mathieu Tarral +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# +# 1. Redistributions of source code must retain the copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# 3. The name of the author may not be used to endorse or promote products +# derived from this software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +# IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +# OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +# IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +# MACRO check_compiler_version +#----------------------------- +macro (check_compiler_version gcc_required_version clang_required_version) + if ( + ( + CMAKE_CXX_COMPILER_ID MATCHES "GNU" + AND + CMAKE_CXX_COMPILER_VERSION VERSION_LESS ${gcc_required_version} + ) + OR + ( + CMAKE_CXX_COMPILER_ID MATCHES "Clang" + AND + CMAKE_CXX_COMPILER_VERSION VERSION_LESS ${clang_required_version} + ) + ) + # error ! + message(FATAL_ERROR "You ask to enable the sanitizer ${CUR_SANITIZER}, + but your compiler ${CMAKE_CXX_COMPILER_ID} version ${CMAKE_CXX_COMPILER_VERSION} + does not support it ! + You should use at least GCC ${gcc_required_version} or Clang ${clang_required_version} + (99.99 means not implemented yet)") + endif () +endmacro () + +# MACRO check_compiler_support +#------------------------------ +macro (enable_sanitizer_flags sanitize_option) + if (${sanitize_option} MATCHES "address") + check_compiler_version("4.8" "3.1") + set(XSAN_COMPILE_FLAGS "-fsanitize=address -fno-omit-frame-pointer -fno-optimize-sibling-calls") + set(XSAN_LINKER_FLAGS "asan") + elseif (${sanitize_option} MATCHES "thread") + check_compiler_version("4.8" "3.1") + set(XSAN_COMPILE_FLAGS "-fsanitize=thread") + set(XSAN_LINKER_FLAGS "tsan") + elseif (${sanitize_option} MATCHES "memory") + check_compiler_version("99.99" "3.1") + set(XSAN_COMPILE_FLAGS "-fsanitize=memory") + elseif (${sanitize_option} MATCHES "leak") + check_compiler_version("4.9" "3.4") + set(XSAN_COMPILE_FLAGS "-fsanitize=leak") + set(XSAN_LINKER_FLAGS "lsan") + elseif (${sanitize_option} MATCHES "undefined") + check_compiler_version("4.9" "3.1") + set(XSAN_COMPILE_FLAGS "-fsanitize=undefined -fno-omit-frame-pointer -fno-optimize-sibling-calls") + else () + message(FATAL_ERROR "Compiler sanitizer option \"${sanitize_option}\" not supported.") + endif () +endmacro () + +if (ECM_ENABLE_SANITIZERS) + if (CMAKE_CXX_COMPILER_ID MATCHES "GNU" OR CMAKE_CXX_COMPILER_ID MATCHES "Clang") + # for each element of the ECM_ENABLE_SANITIZERS list + foreach ( CUR_SANITIZER ${ECM_ENABLE_SANITIZERS} ) + # lowercase filter + string(TOLOWER ${CUR_SANITIZER} CUR_SANITIZER) + # check option and enable appropriate flags + enable_sanitizer_flags ( ${CUR_SANITIZER} ) + # TODO: GCC will not link pthread library if enabled ASan + if(CMAKE_C_COMPILER_ID MATCHES "Clang") + set( CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${XSAN_COMPILE_FLAGS}" ) + endif() + set( CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${XSAN_COMPILE_FLAGS}" ) + if(CMAKE_CXX_COMPILER_ID MATCHES "GNU") + link_libraries(${XSAN_LINKER_FLAGS}) + endif() + if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") + string(REPLACE "-Wl,--no-undefined" "" CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS}") + string(REPLACE "-Wl,--no-undefined" "" CMAKE_MODULE_LINKER_FLAGS "${CMAKE_MODULE_LINKER_FLAGS}") + endif () + endforeach() + else() + message(STATUS "Tried to enable sanitizers (-DECM_ENABLE_SANITIZERS=${ECM_ENABLE_SANITIZERS}), \ +but compiler (${CMAKE_CXX_COMPILER_ID}) does not have sanitizer support") + endif() +endif() diff --git a/Source/cmake/OptionsQt.cmake b/Source/cmake/OptionsQt.cmake index 1930027d1..457fff566 100644 --- a/Source/cmake/OptionsQt.cmake +++ b/Source/cmake/OptionsQt.cmake @@ -1,4 +1,5 @@ include(FeatureSummary) +include(ECMEnableSanitizers) include(ECMPackageConfigHelpers) set(ECM_MODULE_DIR ${CMAKE_MODULE_PATH}) @@ -152,7 +153,21 @@ else () endif () # FIXME: Move Qt handling here -find_package(Qt5Gui QUIET) +set(REQUIRED_QT_VERSION 5.2.0) +find_package(Qt5 ${REQUIRED_QT_VERSION} REQUIRED COMPONENTS Core Gui QUIET) + +get_target_property(QT_CORE_TYPE Qt5::Core TYPE) +if (QT_CORE_TYPE MATCHES STATIC) + set(QT_STATIC_BUILD ON) + set(SHARED_CORE OFF) + set(MACOS_BUILD_FRAMEWORKS OFF) +endif () + +if (QT_STATIC_BUILD) + set(ENABLE_WEBKIT2_DEFAULT OFF) +else () + set(ENABLE_WEBKIT2_DEFAULT ON) +endif () if (UNIX AND TARGET Qt5::QXcbIntegrationPlugin AND NOT APPLE) set(ENABLE_X11_TARGET_DEFAULT ON) @@ -179,7 +194,7 @@ WEBKIT_OPTION_DEFINE(ENABLE_OPENGL "Whether to use OpenGL." PUBLIC ON) WEBKIT_OPTION_DEFINE(ENABLE_PRINT_SUPPORT "Enable support for printing web pages" PUBLIC ON) WEBKIT_OPTION_DEFINE(ENABLE_QT_GESTURE_EVENTS "Enable support for gesture events (required for mouse in WK2)" PUBLIC ON) WEBKIT_OPTION_DEFINE(ENABLE_QT_WEBCHANNEL "Enable support for Qt WebChannel" PUBLIC ON) -WEBKIT_OPTION_DEFINE(ENABLE_WEBKIT2 "Enable WebKit2 (QML API)" PUBLIC ON) +WEBKIT_OPTION_DEFINE(ENABLE_WEBKIT2 "Enable WebKit2 (QML API)" PUBLIC ${ENABLE_WEBKIT2_DEFAULT}) WEBKIT_OPTION_DEFINE(ENABLE_X11_TARGET "Whether to enable support for the X11 windowing target." PUBLIC ${ENABLE_X11_TARGET_DEFAULT}) option(GENERATE_DOCUMENTATION "Generate HTML and QCH documentation" OFF) @@ -249,6 +264,8 @@ if (MINGW AND CMAKE_SIZEOF_VOID_P EQUAL 8) endif () WEBKIT_OPTION_CONFLICT(USE_GSTREAMER USE_QT_MULTIMEDIA) +WEBKIT_OPTION_CONFLICT(USE_GSTREAMER USE_MEDIA_FOUNDATION) +WEBKIT_OPTION_CONFLICT(USE_QT_MULTIMEDIA USE_MEDIA_FOUNDATION) WEBKIT_OPTION_DEPEND(ENABLE_3D_TRANSFORMS ENABLE_OPENGL) WEBKIT_OPTION_DEPEND(ENABLE_ACCELERATED_2D_CANVAS ENABLE_OPENGL) @@ -271,9 +288,9 @@ WEBKIT_OPTION_END() # FTL JIT and IndexedDB support require GCC 4.9 # TODO: Patch code to avoid variadic lambdas if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU") - if (ENABLE_FTL_JIT OR ENABLE_INDEXED_DATABASE) + if (ENABLE_FTL_JIT OR ENABLE_INDEXED_DATABASE OR (ENABLE_WEBKIT2 AND ENABLE_DATABASE_PROCESS)) if (CMAKE_CXX_COMPILER_VERSION VERSION_LESS "4.9.0") - message(FATAL_ERROR "GCC 4.9.0 is required to build QtWebKit with FTL JIT and Indexed Database, use a newer GCC version or clang, or disable these features") + message(FATAL_ERROR "GCC 4.9.0 is required to build QtWebKit with FTL JIT, Indexed Database, and Database Process (WebKit 2). Use a newer GCC version or clang, or disable these features") endif () else () if (CMAKE_CXX_COMPILER_VERSION VERSION_LESS "4.8.0") @@ -291,13 +308,6 @@ endif () set(ENABLE_WEBKIT ON) set(WTF_USE_UDIS86 1) -get_target_property(QT_CORE_TYPE Qt5::Core TYPE) -if (QT_CORE_TYPE MATCHES STATIC) - set(QT_STATIC_BUILD ON) - set(SHARED_CORE OFF) - set(MACOS_BUILD_FRAMEWORKS OFF) -endif () - if (SHARED_CORE) set(WebCoreTestSupport_LIBRARY_TYPE SHARED) else () @@ -431,7 +441,6 @@ if (WEBP_FOUND) SET_AND_EXPOSE_TO_BUILD(USE_WEBP 1) endif () -set(REQUIRED_QT_VERSION 5.2.0) set(QT_REQUIRED_COMPONENTS Core Gui Network) # FIXME: Allow building w/o these components @@ -613,6 +622,7 @@ if (ENABLE_OPENGL) endif () if (NOT ENABLE_VIDEO) + set(USE_MEDIA_FOUNDATION OFF) set(USE_QT_MULTIMEDIA OFF) if (NOT ENABLE_WEB_AUDIO) diff --git a/Source/cmake/WebKitCommon.cmake b/Source/cmake/WebKitCommon.cmake index e617c7cc4..1f7b4ccdf 100644 --- a/Source/cmake/WebKitCommon.cmake +++ b/Source/cmake/WebKitCommon.cmake @@ -25,6 +25,9 @@ if (NOT HAS_RUN_WEBKIT_COMMON) find_package(Perl 5.10.0 REQUIRED) find_package(PythonInterp 2.7.0 REQUIRED) + if (PYTHON_VERSION_MAJOR GREATER 2) + message(FATAL_ERROR "Python 2 is required, but Python ${PYTHON_VERSION_MAJOR} was found.") + endif () # We cannot check for RUBY_FOUND because it is set only when the full package is installed and # the only thing we need is the interpreter. Unlike Python, cmake does not provide a macro diff --git a/Tools/MiniBrowser/qt/icons/find.png b/Tools/MiniBrowser/qt/icons/find.png index b76afa398..eb5a0ad97 100644 Binary files a/Tools/MiniBrowser/qt/icons/find.png and b/Tools/MiniBrowser/qt/icons/find.png differ diff --git a/Tools/MiniBrowser/qt/icons/plus.png b/Tools/MiniBrowser/qt/icons/plus.png index f6dfbd02d..671a23d38 100644 Binary files a/Tools/MiniBrowser/qt/icons/plus.png and b/Tools/MiniBrowser/qt/icons/plus.png differ diff --git a/Tools/MiniBrowser/qt/icons/touch.png b/Tools/MiniBrowser/qt/icons/touch.png index 182ae0fe8..4d956c5b6 100644 Binary files a/Tools/MiniBrowser/qt/icons/touch.png and b/Tools/MiniBrowser/qt/icons/touch.png differ diff --git a/Tools/qmake/projects/run_cmake.pro b/Tools/qmake/projects/run_cmake.pro index 5603ed72e..fcab90880 100644 --- a/Tools/qmake/projects/run_cmake.pro +++ b/Tools/qmake/projects/run_cmake.pro @@ -12,6 +12,8 @@ CONFIG(debug, debug|release) { configuration = Release } +programExistsInPath(ninja): use_ninja = 1 + cmake_build_dir = $$system_quote($$system_path($$ROOT_BUILD_DIR/$$lower($$configuration))) toolchain_file = $$system_quote($$system_path($$ROOT_BUILD_DIR/qmake_toolchain.cmake)) @@ -82,6 +84,8 @@ build_pass|!debug_and_release { } } + !isEmpty(use_ninja): cmake_args += "-G Ninja" + equals(QMAKE_HOST.os, Windows) { if(equals(MAKEFILE_GENERATOR, MSVC.NET)|equals(MAKEFILE_GENERATOR, MSBUILD)) { cmake_generator = "NMake Makefiles JOM" @@ -93,10 +97,15 @@ build_pass|!debug_and_release { cmake_generator = "Unix Makefiles" make_command_name = make } - cmake_args += "-G \"$$cmake_generator\"" + isEmpty(use_ninja): cmake_args += "-G \"$$cmake_generator\"" + } else { + make_command_name = make } - !silent: make_args += "VERBOSE=1" + !silent { + make_args += "VERBOSE=1" + ninja_args += "-v" + } # Append additional platform options defined in CMAKE_CONFIG for (config, CMAKE_CONFIG): cmake_args += "-D$$config" @@ -115,7 +124,12 @@ build_pass|!debug_and_release { build_pass:build_all: default_target.target = all else: default_target.target = first - default_target.commands = cd $$cmake_build_dir && $(MAKE) $$make_args + + isEmpty(use_ninja) { + default_target.commands = cd $$cmake_build_dir && $(MAKE) $$make_args + } else { + default_target.commands = cd $$cmake_build_dir && ninja $$ninja_args + } QMAKE_EXTRA_TARGETS += default_target # When debug and release are built at the same time, don't install data files twice @@ -129,3 +143,10 @@ build_pass|!debug_and_release { install_target.commands = $(MAKE) -f $(MAKEFILE) install_impl $$make_args DESTDIR=$(INSTALL_ROOT) QMAKE_EXTRA_TARGETS += install_target } + +!build_pass:debug_and_release:!isEmpty(use_ninja) { + # Special GNU make target for the meta Makefile that ensures that our + # debug_and_release Makefiles won't both run ninja in parallel. + notParallel.target = .NOTPARALLEL + QMAKE_EXTRA_TARGETS += notParallel +} -- cgit v1.2.3