I'm trying to add '@Description attributes to api declarations with conditional compilation, like this:
'@Description("API: Destination and Source can be byVal pointers or byRef variables, length is LenB(dataType)")
#If Win64 Then
Private Declare PtrSafe Sub CopyMemory Lib "kernel32.dll" Alias "RtlMoveMemory" (ByRef Destination As Any, ByRef Source As Any, ByVal length As Long)
#Else
Private Declare Sub CopyMemory Lib "kernel32.dll" Alias "RtlMoveMemory" (ByRef Destination As Any, ByRef Source As Any, ByVal length As Long)
#End If
The inspections detect it fine but the quickfix does nothing, is this sort of thing supported?
Rubberduck is only seeing the "live" code (IIRC with whitespace in place of the "dead" code), so stuff around conditionally compiled code is always going to be a rough edge.
Does it work better if you put the annotation inside the conditionally compiled block?
#If Win64 Then
'@Description("API: Destination and Source can be byVal pointers or byRef variables, length is LenB(dataType)")
Private Declare PtrSafe Sub CopyMemory Lib "kernel32.dll" Alias "RtlMoveMemory" (ByRef Destination As Any, ByRef Source As Any, ByVal length As Long)
#Else
'@Description("API: Destination and Source can be byVal pointers or byRef variables, length is LenB(dataType)")
Private Declare Sub CopyMemory Lib "kernel32.dll" Alias "RtlMoveMemory" (ByRef Destination As Any, ByRef Source As Any, ByVal length As Long)
#End If
I thought that might be the case. No, that change doesn't solve the problem; I'm getting errors in the log like this one:
2019-06-28 14:46:41.1293;ERROR-2.4.1.4694;Rubberduck.UI.Inspections.InspectionResultsViewModel;System.NullReferenceException: Object reference not set to an instance of an object.
at Rubberduck.Parsing.VBA.AttributesUpdater.AddAttribute(IRewriteSession rewriteSession, Declaration declaration, String attribute, IReadOnlyList`1 values) in C:\projects\rubberduck\Rubberduck.Parsing\VBA\AttributesUpdater.cs:line 99
at Rubberduck.Inspections.QuickFixes.AddMissingAttributeQuickFix.Fix(IInspectionResult result, IRewriteSession rewriteSession) in C:\projects\rubberduck\Rubberduck.CodeAnalysis\QuickFixes\AddMissingAttributeQuickFix.cs:line 31
at Rubberduck.Inspections.QuickFixes.QuickFixProvider.FixInProject(IQuickFix fix, QualifiedSelection selection, Type inspectionType, IEnumerable`1 results) in C:\projects\rubberduck\Rubberduck.CodeAnalysis\QuickFixes\QuickFixProvider.cs:line 177
at Rubberduck.UI.Inspections.InspectionResultsViewModel.ExecuteQuickFixInProjectCommand(Object parameter) in C:\projects\rubberduck\Rubberduck.Core\UI\Inspections\InspectionResultsViewModel.cs:line 580
at Rubberduck.UI.Command.DelegateCommand.OnExecute(Object parameter) in C:\projects\rubberduck\Rubberduck.Core\UI\Command\DelegateCommand.cs:line 29
at Rubberduck.UI.Command.CommandBase.Execute(Object parameter) in C:\projects\rubberduck\Rubberduck.Core\UI\Command\CommandBase.cs:line 60;System.NullReferenceException: Object reference not set to an instance of an object.
at Rubberduck.Parsing.VBA.AttributesUpdater.AddAttribute(IRewriteSession rewriteSession, Declaration declaration, String attribute, IReadOnlyList`1 values) in C:\projects\rubberduck\Rubberduck.Parsing\VBA\AttributesUpdater.cs:line 99
at Rubberduck.Inspections.QuickFixes.AddMissingAttributeQuickFix.Fix(IInspectionResult result, IRewriteSession rewriteSession) in C:\projects\rubberduck\Rubberduck.CodeAnalysis\QuickFixes\AddMissingAttributeQuickFix.cs:line 31
at Rubberduck.Inspections.QuickFixes.QuickFixProvider.FixInProject(IQuickFix fix, QualifiedSelection selection, Type inspectionType, IEnumerable`1 results) in C:\projects\rubberduck\Rubberduck.CodeAnalysis\QuickFixes\QuickFixProvider.cs:line 177
at Rubberduck.UI.Inspections.InspectionResultsViewModel.ExecuteQuickFixInProjectCommand(Object parameter) in C:\projects\rubberduck\Rubberduck.Core\UI\Inspections\InspectionResultsViewModel.cs:line 580
at Rubberduck.UI.Command.DelegateCommand.OnExecute(Object parameter) in C:\projects\rubberduck\Rubberduck.Core\UI\Command\DelegateCommand.cs:line 29
at Rubberduck.UI.Command.CommandBase.Execute(Object parameter) in C:\projects\rubberduck\Rubberduck.Core\UI\Command\CommandBase.cs:line 60
...when I try the quickfix.
I also tried getting rid of the 1st '@Description (I'm 32 bit system)
#If Win64 Then
Private Declare PtrSafe Sub CopyMemory Lib "kernel32.dll" Alias "RtlMoveMemory" (ByRef Destination As Any, ByRef Source As Any, ByVal length As Long)
#Else
'@Description("API: Destination and Source can be byVal pointers or byRef variables, length is LenB(dataType)")
Private Declare Sub CopyMemory Lib "kernel32.dll" Alias "RtlMoveMemory" (ByRef Destination As Any, ByRef Source As Any, ByVal length As Long)
#End If
but still no luck
I will have to test this case. It might be that the attribute gets added outside the procedure, which would cause the VBE to ignore it.
Another possibility is that it gets added in the wrong branch of the conditional compilation.
I think part of the problem is that we require annotations to be above the member and the VBE demands attributes to be inside or right below the member.
Hm, looking at the stack trace, there is definitely a bug. I will have to find some time to look into this.
The problem is not the conditional compilation. That works just fine.
The problem here is that the attribute annotation is on a declare statement. AFAIK, that is not legal; we do not collect the corresponding context from the attributes pass.
So, from my point of view the problem here is that there was an inspection result for the missing attribute in the first place instead of one for an illegal annotation.
FWIW, it seems to me we can at least add a description to the Declare statements.
Public Declare PtrSafe Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long)
Attribute Sleep.VB_Description = "Can I haz a description?"


Note that the description doesn't show up right away but does after an import (and perhaps after restart?)
For those who like a horror show....

Most helpful comment
For those who like a horror show....