From 279a1c527003811333646bcb827fda38618d8f21 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Michael=20M=C3=BCller?= <michael@fds-team.de>
Date: Sun, 20 Dec 2015 22:15:45 +0100
Subject: nvencodeapi: Add support for version 6.0.

---
 dlls/nvencodeapi/nvencodeapi.c | 51 ++++++++++++++++++++++++++++++++----------
 include/nvencodeapi.h          | 21 +++++++++++++++--
 2 files changed, 58 insertions(+), 14 deletions(-)

diff --git a/dlls/nvencodeapi/nvencodeapi.c b/dlls/nvencodeapi/nvencodeapi.c
index 557c6ae..1a03a0b 100644
--- a/dlls/nvencodeapi/nvencodeapi.c
+++ b/dlls/nvencodeapi/nvencodeapi.c
@@ -264,18 +264,50 @@ static NVENCSTATUS WINAPI NvEncReconfigureEncoder(void *encoder, NV_ENC_RECONFIG
     return origFunctions.nvEncReconfigureEncoder(encoder, reInitEncodeParams);
 }
 
+static NVENCSTATUS WINAPI NvEncCreateMVBuffer(void *encoder, NV_ENC_CREATE_MV_BUFFER *createMVBufferParams)
+{
+    TRACE("(%p, %p)\n", encoder, createMVBufferParams);
+    return origFunctions.nvEncCreateMVBuffer(encoder, createMVBufferParams);
+}
+
+static NVENCSTATUS WINAPI NvEncDestroyMVBuffer(void *encoder, NV_ENC_OUTPUT_PTR MVBuffer)
+{
+    TRACE("(%p, %p)\n", encoder, MVBuffer);
+    return origFunctions.nvEncDestroyMVBuffer(encoder, MVBuffer);
+}
+
+static NVENCSTATUS WINAPI NvEncRunMotionEstimationOnly(void *encoder, NV_ENC_MEONLY_PARAMS *MEOnlyParams)
+{
+    TRACE("(%p, %p)\n", encoder, MEOnlyParams);
+    return origFunctions.nvEncRunMotionEstimationOnly(encoder, MEOnlyParams);
+}
 
 NVENCSTATUS WINAPI NvEncodeAPICreateInstance(NV_ENCODE_API_FUNCTION_LIST *functionList)
 {
+    NVENCSTATUS status;
+
     TRACE("(%p)\n", functionList);
 
     if (!functionList)
         return NV_ENC_ERR_INVALID_PTR;
 
-    /* FIXME: Provide forward/backwards compatibility */
-    if (functionList->version != NV_ENCODE_API_FUNCTION_LIST_VER)
-        FIXME("Application expects nvencodeapi version %x, but wrapper only supports version %x\n",
-              functionList->version, NV_ENCODE_API_FUNCTION_LIST_VER);
+    /* we currently support 5.0 and 6.0 */
+    if (functionList->version != NV_ENCODE_API_FUNCTION_LIST_VER &&
+        functionList->version != NV_ENCODE_API_FUNCTION_LIST_VER_6_0)
+    {
+        FIXME("Application requested nvencodeapi version %x which is not supported yet\n",
+              functionList->version);
+        return NV_ENC_ERR_INVALID_VERSION;
+    }
+
+    memset(&origFunctions, 0, sizeof(origFunctions));
+    origFunctions.version = functionList->version;
+    status = pNvEncodeAPICreateInstance(&origFunctions);
+    if (status)
+    {
+        FIXME("Failed to create native encoder for version %x\n", functionList->version);
+        return status;
+    }
 
     /* set all function points and reserved values to zero */
     memset(functionList, 0, sizeof(*functionList));
@@ -316,6 +348,9 @@ NVENCSTATUS WINAPI NvEncodeAPICreateInstance(NV_ENCODE_API_FUNCTION_LIST *functi
     SET_FUNCPTR(EncRegisterResource);
     SET_FUNCPTR(EncUnregisterResource);
     SET_FUNCPTR(EncReconfigureEncoder);
+    SET_FUNCPTR(EncCreateMVBuffer);             /* available since 6.0 */
+    SET_FUNCPTR(EncDestroyMVBuffer);            /* available since 6.0 */
+    SET_FUNCPTR(EncRunMotionEstimationOnly);    /* available since 6.0 */
 
     #undef SET_FUNCPTR
 
@@ -354,14 +389,6 @@ static BOOL load_nvencode(void)
         return FALSE;
     }
 
-    memset(&origFunctions, 0, sizeof(origFunctions));
-    origFunctions.version = NV_ENCODE_API_FUNCTION_LIST_VER;
-    if (pNvEncodeAPICreateInstance(&origFunctions))
-    {
-        FIXME("Failed to get function pointers.\n");
-        return FALSE;
-    }
-
     return TRUE;
 }
 
diff --git a/include/nvencodeapi.h b/include/nvencodeapi.h
index 45e9fb9..3e44dd3 100644
--- a/include/nvencodeapi.h
+++ b/include/nvencodeapi.h
@@ -27,6 +27,12 @@
 #define NVENCAPI_VERSION ((NVENCAPI_MAJOR_VERSION << 4) | (NVENCAPI_MINOR_VERSION))
 #define NVENCAPI_STRUCT_VERSION(type, version) (uint32_t)(sizeof(type) | ((version)<<16) | (NVENCAPI_VERSION << 24))
 
+/* the version scheme changed between 5.0 and 6.0 */
+#define NVENCAPI_MAJOR_VERSION_6 6
+#define NVENCAPI_MINOR_VERSION_0 0
+#define NVENCAPI_VERSION_6_0 (NVENCAPI_MAJOR_VERSION_6 | (NVENCAPI_MINOR_VERSION_0 << 24))
+#define NVENCAPI_STRUCT_VERSION_6_0(ver) ((uint32_t)NVENCAPI_VERSION_6_0 | ((ver)<<16) | (0x7 << 28))
+
 #define NVENCSTATUS int
 #define NV_ENC_SUCCESS 0
 #define NV_ENC_ERR_INVALID_PTR 6
@@ -59,6 +65,8 @@ typedef struct _NV_ENC_EVENT_PARAMS NV_ENC_EVENT_PARAMS;
 typedef struct _NV_ENC_OPEN_ENCODE_SESSIONEX_PARAMS NV_ENC_OPEN_ENCODE_SESSIONEX_PARAMS;
 typedef struct _NV_ENC_BUFFER_FORMAT NV_ENC_BUFFER_FORMAT;
 typedef struct _NV_ENC_OPEN_ENCODE_SESSION_EX_PARAMS NV_ENC_OPEN_ENCODE_SESSION_EX_PARAMS;
+typedef struct _NV_ENC_CREATE_MV_BUFFER NV_ENC_CREATE_MV_BUFFER;
+typedef struct _NV_ENC_MEONLY_PARAMS NV_ENC_MEONLY_PARAMS;
 
 typedef struct _NVENC_EXTERNAL_ME_HINT_COUNTS_PER_BLOCKTYPE
 {
@@ -230,10 +238,15 @@ typedef struct __NV_ENCODE_API_FUNCTION_LIST
     NVENCSTATUS (WINAPI *nvEncRegisterResource)(void *encoder, NV_ENC_REGISTER_RESOURCE *registerResParams);
     NVENCSTATUS (WINAPI *nvEncUnregisterResource)(void *encoder, NV_ENC_REGISTERED_PTR registeredRes);
     NVENCSTATUS (WINAPI *nvEncReconfigureEncoder)(void *encoder, NV_ENC_RECONFIGURE_PARAMS *reInitEncodeParams);
-    void *reserved2[285];
+    void *reserved1;
+    NVENCSTATUS (WINAPI *nvEncCreateMVBuffer)(void *encoder, NV_ENC_CREATE_MV_BUFFER *createMVBufferParams);
+    NVENCSTATUS (WINAPI *nvEncDestroyMVBuffer)(void *encoder, NV_ENC_OUTPUT_PTR MVBuffer);
+    NVENCSTATUS (WINAPI *nvEncRunMotionEstimationOnly)(void *encoder, NV_ENC_MEONLY_PARAMS *MEOnlyParams);
+    void *reserved2[281];
 } NV_ENCODE_API_FUNCTION_LIST;
 
 #define NV_ENCODE_API_FUNCTION_LIST_VER NVENCAPI_STRUCT_VERSION(NV_ENCODE_API_FUNCTION_LIST, 2)
+#define NV_ENCODE_API_FUNCTION_LIST_VER_6_0 NVENCAPI_STRUCT_VERSION_6_0(2)
 
 typedef struct __LINUX_NV_ENCODE_API_FUNCTION_LIST
 {
@@ -275,7 +288,11 @@ typedef struct __LINUX_NV_ENCODE_API_FUNCTION_LIST
     NVENCSTATUS (*nvEncRegisterResource)(void *encoder, NV_ENC_REGISTER_RESOURCE *registerResParams);
     NVENCSTATUS (*nvEncUnregisterResource)(void *encoder, NV_ENC_REGISTERED_PTR registeredRes);
     NVENCSTATUS (*nvEncReconfigureEncoder)(void *encoder, NV_ENC_RECONFIGURE_PARAMS *reInitEncodeParams);
-    void *reserved2[285];
+    void *reserved1;
+    NVENCSTATUS (*nvEncCreateMVBuffer)(void *encoder, NV_ENC_CREATE_MV_BUFFER *createMVBufferParams);
+    NVENCSTATUS (*nvEncDestroyMVBuffer)(void *encoder, NV_ENC_OUTPUT_PTR MVBuffer);
+    NVENCSTATUS (*nvEncRunMotionEstimationOnly)(void *encoder, NV_ENC_MEONLY_PARAMS *MEOnlyParams);
+    void *reserved2[281];
 } LINUX_NV_ENCODE_API_FUNCTION_LIST;
 
 #endif /* __WINE_NVENCODEAPI_H */
-- 
2.6.4

