Revit 2016 R2 在 UIApplication.OpenAndActivateDocument 上崩溃
Revit 2016 R2 Crashes on UIApplication.OpenAndActivateDocument
背景
我有一个 Revit 2016 加载项,可以从主模型及其链接模型批量导出到 DWF。它的工作原理是从主模型导出图纸并循环遍历链接模型以导出其他图纸。它使用 UIApplication.OpenAndActivateDocument
打开文档,使用 Document.Close
关闭文档。因为 Revit API 不允许您关闭活动文档,所以它必须先打开一个占位符文档,然后才能关闭活动文档并打开下一个文档。这至少从 Revit 2014 开始就有效,但自 Revit 2016 R2 发布以来就停止工作了。
现在,当您导出多张工作表时,调用 UIApplication.OpenAndActivateDocument
会失败。即使使用最新版本的 Revit 2016 R2 Update 4,问题仍然存在。
错误
错误是从 UIApplication.OpenAndActivateDocument
方法中抛出的。它看起来像这样:
System.ComponentModel.Win32Exception was unhandled
ErrorCode=-2147467259 HResult=-2147467259 Message=Not enough quota is
available to process this command NativeErrorCode=1816
Source=WindowsBase StackTrace: at
MS.Win32.UnsafeNativeMethods.PostMessage(HandleRef hwnd, WindowMessage
msg, IntPtr wparam, IntPtr lparam) at
System.Windows.Interop.HwndTarget.UpdateWindowSettings(Boolean
enableRenderTarget, Nullable`1 channelSet) at
System.Windows.Interop.HwndTarget.UpdateWindowPos(IntPtr lParam) at
System.Windows.Interop.HwndTarget.HandleMessage(WindowMessage msg,
IntPtr wparam, IntPtr lparam) at
System.Windows.Interop.HwndSource.HwndTargetFilterMessage(IntPtr hwnd,
Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled) at
MS.Win32.HwndWrapper.WndProc(IntPtr hwnd, Int32 msg, IntPtr wParam,
IntPtr lParam, Boolean& handled) at
MS.Win32.HwndSubclass.DispatcherCallbackOperation(Object o) at
System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate
callback, Object args, Int32 numArgs) at
System.Windows.Threading.ExceptionWrapper.TryCatchWhen(Object source,
Delegate callback, Object args, Int32 numArgs, Delegate catchHandler)
at
System.Windows.Threading.Dispatcher.LegacyInvokeImpl(DispatcherPriority
priority, TimeSpan timeout, Delegate method, Object args, Int32
numArgs) at MS.Win32.HwndSubclass.SubclassWndProc(IntPtr hwnd, Int32
msg, IntPtr wParam, IntPtr lParam)
这是日志文件末尾显示的内容:
' 2.510552 2:<
' 1:< ***NOBLE invalidated secondary data id = 130129 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 130130 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 130131 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 130134 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 138258 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 138259 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 138983 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 140000 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 5964554 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 6073456 due to the modified link document.
' 1:< 0 ModelServerState "Destroyed": Current server = "Not Queried", Model server = "", Model server state = "Not Applicable"
' 6:< --TB- Level 368 - Levels : Level : FF EL
' 0.104902 6:<<--TB- recomputeCircuits
' 1.094590!!!!! 4:!!!BIG_GAP ;PERF;MISC;regenerating
' 1.315856 3:<<;PERF;MISC;regenerating/ALL_GAPS 1.210954/TurnOff_GAPs 100%
' 1:< Managed exception occurred:
'C 03-May-2016 08:43:03.892; 1:< Not enough quota is available to process this command
'C 03-May-2016 08:43:03.892; 1:< ExceptionCode=0xe0434352 ExceptionFlags=0x00000001 ExceptionAddress=000007FEFCD0A06D
' 1:< System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< RAM Statistics: 9845/ 16323 3199=InUse 3243=Peak
' 1:< VM Statistics: 8381636 / 8388607 3089=InUse 3120=Peak
' 0:< [00002088]QueueMinder stopped
' 2:< ::100:: Delta VM: Avail +3 -> 8381638 MB, Used 3089 MB; RAM: Avail +109 -> 9955 MB, Used -1 -> 3198 MB
'C 03-May-2016 08:43:04.652; 2:< OMICRON finished virtualization services
'C 03-May-2016 08:43:04.652; 2:< OMICRON finished worker services
'C 03-May-2016 08:43:04.652; 2:< OMICRON erased queues
' 0.760501 2:<<
' 1:< SLOG 60798f 2016-05-03 08:43:04.736 >Crash
' 1:< SLOG System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< SLOG RAM Statistics: 9957 / 16323 3198=InUse 3243=Peak
' 1:< SLOG VM Statistics: 8381643 / 8388607 3089=InUse 3120=Peak
' 1:< SLOG 60798f 2016-05-03 08:43:04.746
' 1:< FileCheckTrigger dependencies update
' 1:< Third Party Updater 'Revit: ObjectNumberingUpdater' has been unregistered.
' 1:< Third Party Updater 'Revit: ObjectNumberingUpdater' has been unregistered.
' 1:< Before : Destroy Display Manager
' 1:< System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< RAM Statistics: 9956 / 16323 3198=InUse 3243=Peak
' 1:< VM Statistics: 8381643 / 8388607 3089=InUse 3120=Peak
' 1:< After : Destroy Display Manager
' 1:< System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< RAM Statistics: 9956 / 16323 3198=InUse 3243=Peak
' 1:< VM Statistics: 8381643 / 8388607 3089=InUse 3120=Peak
' 1:< compact data space: 380388 blocks, occupying total of 165719148 bytes > ' 1:< freed 380388 blocks
' 2:<::100:: Delta VM: Avail +36 -> 8381675 MB, Used 3089 MB; RAM: Avail -2 -> 9953 MB, Used -1 -> 3197 MB
' 2:< DBG_INFO: Detected unfrozen change of selection.: line 609 of d:\sunrise16_px64\source\revit\revitui\modscope\ModScope.cpp.
' 2:< ;PERF;MISC;FullUpdateGraphicCacheUpdater::updateAll() DBViewProject id=275: 2545 elements need cache update
' 1:< Unconverted MessageBox "A fatal error has occurred. The application will be terminated. You have the opportunity to save recovery files for all of your changed projects.
理论
我猜测问题已经开始,因为 2016 R2 中引入的新功能导致 DWF 使用多个进程而不是像以前版本中的单个进程导出。我已尝试 post my problem on the Autodesk Forums 但尚未收到他们支持的回复。
我也猜测它与内存有关,因为我从几个互联网资源中了解到 "Not enough quota is available to process this command message" 但我的机器有 16GB 的 RAM,应该适合 Revit。
还有其他人有什么想法吗?
我从 this question about DataGrid 中找到了有关错误 "Not enough quota was available to process this command" 的更多信息。显然这个问题与 Windows UI 消息队列有关,我必须承认我并不完全理解。这些底层 PostMessage
函数调用有一个队列,默认调用限制为 10,000。达到此限制时发送配额错误。我无法控制底层 Revit 代码,所以我只是决定增加此限制(存储为注册表项)并且对我有用(在重新启动计算机后)。我的解决方案是将以下注册表项设置为 1,000,000:
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\WindowsNT\CurrentVersion\Windows\USERPostMessageLimit
我最初尝试了 20,000,但错误仍然出现,所以我选择了一个任意高的数字 1,000,000,然后错误消失了。然后我开始以较低的值测试我们最大的模型,500,000 的值是不会触发错误的最低可能设置。现在我让单个用户 运行 以这种方式配置它,因为我不确定它是否会导致其他 Windows 应用程序出现问题,因为它影响的不仅仅是 Revit。
我找到了一种重组我的程序的方法,这样它就不会调用包含当前模型中所有 sheet 的 ViewSet
一次 Document.Export
Document.Export
通过传入包含单个 sheet 的 ViewSet
对当前模型中的每个 sheet 一次。无论出于何种原因,这都会阻止 Revit 崩溃,可能是因为它放弃了通常会导致崩溃的资源。
请注意,执行此操作后,DWF 将按顺序导出,而不是并行导出,因为只有在一次调用中传入多个 sheet,您才能利用 Revit 2016 中引入的多进程导出R2。具有讽刺意味的是,顺序方法和并行方法一样快。
背景
我有一个 Revit 2016 加载项,可以从主模型及其链接模型批量导出到 DWF。它的工作原理是从主模型导出图纸并循环遍历链接模型以导出其他图纸。它使用 UIApplication.OpenAndActivateDocument
打开文档,使用 Document.Close
关闭文档。因为 Revit API 不允许您关闭活动文档,所以它必须先打开一个占位符文档,然后才能关闭活动文档并打开下一个文档。这至少从 Revit 2014 开始就有效,但自 Revit 2016 R2 发布以来就停止工作了。
现在,当您导出多张工作表时,调用 UIApplication.OpenAndActivateDocument
会失败。即使使用最新版本的 Revit 2016 R2 Update 4,问题仍然存在。
错误
错误是从 UIApplication.OpenAndActivateDocument
方法中抛出的。它看起来像这样:
System.ComponentModel.Win32Exception was unhandled ErrorCode=-2147467259 HResult=-2147467259 Message=Not enough quota is available to process this command NativeErrorCode=1816 Source=WindowsBase StackTrace: at MS.Win32.UnsafeNativeMethods.PostMessage(HandleRef hwnd, WindowMessage msg, IntPtr wparam, IntPtr lparam) at System.Windows.Interop.HwndTarget.UpdateWindowSettings(Boolean enableRenderTarget, Nullable`1 channelSet) at System.Windows.Interop.HwndTarget.UpdateWindowPos(IntPtr lParam) at System.Windows.Interop.HwndTarget.HandleMessage(WindowMessage msg, IntPtr wparam, IntPtr lparam) at System.Windows.Interop.HwndSource.HwndTargetFilterMessage(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled) at MS.Win32.HwndWrapper.WndProc(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam, Boolean& handled) at MS.Win32.HwndSubclass.DispatcherCallbackOperation(Object o) at System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate callback, Object args, Int32 numArgs) at System.Windows.Threading.ExceptionWrapper.TryCatchWhen(Object source, Delegate callback, Object args, Int32 numArgs, Delegate catchHandler) at System.Windows.Threading.Dispatcher.LegacyInvokeImpl(DispatcherPriority priority, TimeSpan timeout, Delegate method, Object args, Int32 numArgs) at MS.Win32.HwndSubclass.SubclassWndProc(IntPtr hwnd, Int32 msg, IntPtr wParam, IntPtr lParam)
这是日志文件末尾显示的内容:
' 2.510552 2:< ' 1:< ***NOBLE invalidated secondary data id = 130129 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 130130 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 130131 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 130134 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 138258 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 138259 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 138983 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 140000 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 5964554 due to the modified link document.
' 1:< ***NOBLE invalidated secondary data id = 6073456 due to the modified link document.
' 1:< 0 ModelServerState "Destroyed": Current server = "Not Queried", Model server = "", Model server state = "Not Applicable"
' 6:< --TB- Level 368 - Levels : Level : FF EL
' 0.104902 6:<<--TB- recomputeCircuits
' 1.094590!!!!! 4:!!!BIG_GAP ;PERF;MISC;regenerating
' 1.315856 3:<<;PERF;MISC;regenerating/ALL_GAPS 1.210954/TurnOff_GAPs 100%
' 1:< Managed exception occurred:
'C 03-May-2016 08:43:03.892; 1:< Not enough quota is available to process this command
'C 03-May-2016 08:43:03.892; 1:< ExceptionCode=0xe0434352 ExceptionFlags=0x00000001 ExceptionAddress=000007FEFCD0A06D
' 1:< System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< RAM Statistics: 9845/ 16323 3199=InUse 3243=Peak
' 1:< VM Statistics: 8381636 / 8388607 3089=InUse 3120=Peak
' 0:< [00002088]QueueMinder stopped
' 2:< ::100:: Delta VM: Avail +3 -> 8381638 MB, Used 3089 MB; RAM: Avail +109 -> 9955 MB, Used -1 -> 3198 MB
'C 03-May-2016 08:43:04.652; 2:< OMICRON finished virtualization services
'C 03-May-2016 08:43:04.652; 2:< OMICRON finished worker services
'C 03-May-2016 08:43:04.652; 2:< OMICRON erased queues
' 0.760501 2:<< ' 1:< SLOG 60798f 2016-05-03 08:43:04.736 >Crash
' 1:< SLOG System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< SLOG RAM Statistics: 9957 / 16323 3198=InUse 3243=Peak
' 1:< SLOG VM Statistics: 8381643 / 8388607 3089=InUse 3120=Peak
' 1:< SLOG 60798f 2016-05-03 08:43:04.746 ' 1:< FileCheckTrigger dependencies update
' 1:< Third Party Updater 'Revit: ObjectNumberingUpdater' has been unregistered.
' 1:< Third Party Updater 'Revit: ObjectNumberingUpdater' has been unregistered.
' 1:< Before : Destroy Display Manager
' 1:< System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< RAM Statistics: 9956 / 16323 3198=InUse 3243=Peak
' 1:< VM Statistics: 8381643 / 8388607 3089=InUse 3120=Peak
' 1:< After : Destroy Display Manager
' 1:< System (MB) [Available / Total ] [Revit Memory Usage (MB) ]
' 1:< RAM Statistics: 9956 / 16323 3198=InUse 3243=Peak
' 1:< VM Statistics: 8381643 / 8388607 3089=InUse 3120=Peak
' 1:< compact data space: 380388 blocks, occupying total of 165719148 bytes > ' 1:< freed 380388 blocks
' 2:<::100:: Delta VM: Avail +36 -> 8381675 MB, Used 3089 MB; RAM: Avail -2 -> 9953 MB, Used -1 -> 3197 MB
' 2:< DBG_INFO: Detected unfrozen change of selection.: line 609 of d:\sunrise16_px64\source\revit\revitui\modscope\ModScope.cpp.
' 2:< ;PERF;MISC;FullUpdateGraphicCacheUpdater::updateAll() DBViewProject id=275: 2545 elements need cache update
' 1:< Unconverted MessageBox "A fatal error has occurred. The application will be terminated. You have the opportunity to save recovery files for all of your changed projects.
理论
我猜测问题已经开始,因为 2016 R2 中引入的新功能导致 DWF 使用多个进程而不是像以前版本中的单个进程导出。我已尝试 post my problem on the Autodesk Forums 但尚未收到他们支持的回复。
我也猜测它与内存有关,因为我从几个互联网资源中了解到 "Not enough quota is available to process this command message" 但我的机器有 16GB 的 RAM,应该适合 Revit。
还有其他人有什么想法吗?
我从 this question about DataGrid 中找到了有关错误 "Not enough quota was available to process this command" 的更多信息。显然这个问题与 Windows UI 消息队列有关,我必须承认我并不完全理解。这些底层 PostMessage
函数调用有一个队列,默认调用限制为 10,000。达到此限制时发送配额错误。我无法控制底层 Revit 代码,所以我只是决定增加此限制(存储为注册表项)并且对我有用(在重新启动计算机后)。我的解决方案是将以下注册表项设置为 1,000,000:
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\WindowsNT\CurrentVersion\Windows\USERPostMessageLimit
我最初尝试了 20,000,但错误仍然出现,所以我选择了一个任意高的数字 1,000,000,然后错误消失了。然后我开始以较低的值测试我们最大的模型,500,000 的值是不会触发错误的最低可能设置。现在我让单个用户 运行 以这种方式配置它,因为我不确定它是否会导致其他 Windows 应用程序出现问题,因为它影响的不仅仅是 Revit。
我找到了一种重组我的程序的方法,这样它就不会调用包含当前模型中所有 sheet 的 ViewSet
一次 Document.Export
Document.Export
通过传入包含单个 sheet 的 ViewSet
对当前模型中的每个 sheet 一次。无论出于何种原因,这都会阻止 Revit 崩溃,可能是因为它放弃了通常会导致崩溃的资源。
请注意,执行此操作后,DWF 将按顺序导出,而不是并行导出,因为只有在一次调用中传入多个 sheet,您才能利用 Revit 2016 中引入的多进程导出R2。具有讽刺意味的是,顺序方法和并行方法一样快。