Skip to content

return valid text for list views in 64-bit mode#8190

Closed
Robert-J-H wants to merge 11 commits into
nvaccess:masterfrom
Robert-J-H:sysListView32
Closed

return valid text for list views in 64-bit mode#8190
Robert-J-H wants to merge 11 commits into
nvaccess:masterfrom
Robert-J-H:sysListView32

Conversation

@Robert-J-H

@Robert-J-H Robert-J-H commented Apr 18, 2018

Copy link
Copy Markdown
Contributor

Link to issue number:

Closes #8175

Summary of the issue:

Item text in a list view can't be retrieved if the returned pointer is 64 bits long.
Example: Tortoise SVN on a 64-bit machine.
Currently, no exception handling is performed for this case.

Description of how this pull request fixes the issue:

The workaround will first attempt to get the item text by the native procedure.
If this fails, the item text will be retrieved from the display text instead.
Care is taken to limit the text to the column width without splitting words if possible.

Testing performed:

Only with Tortoise SVN.
Navigating with arrow keys works fine, so does table navigation.

Known issues with pull request:

Tortoise's list view has some peculiarities itself that aren't addressed with this commit.
For instance, the first and last entries for an update are not related to the headers, thus,
"Update completed at: Revision xxx" will be rendered as

"Update completed at: Path Revision xxx" if announcing of headers is enabled.

Change log entry:

Not changed yet, would probably go under

Bug fixes

Item text in a list view can't be retrieved if the returned pointer is 64 bits long.
Therefore, return the displayText within the column boundaries instead.

@LeonarddeR LeonarddeR left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for your pr. I have some suggestions that might make your code a bit more compact and, though a bit trivial, might also improve performance.

try:
return self._getColumnContentRaw(targetColumn)
except ArgumentError:
# In case that a 64-bit pointer to the text had been returned /rjh

@LeonarddeR LeonarddeR Apr 18, 2018

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Initials are usually not used in comments. If it is required to contact the comments author, we can use git blame for that.

However, it might be good to point at the issue you reported. e.g. # #8175: In case that a 64-bit pointer to the text had been returned, use the display text

return self._getColumnContentRaw(targetColumn)
except ArgumentError:
# In case that a 64-bit pointer to the text had been returned /rjh
disp = DisplayModelTextInfo(self, 'all')

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Instead of 'all', use textInfos.POSITION_ALL. However, personally I'd first try a different approach, see below.

except ArgumentError:
# In case that a 64-bit pointer to the text had been returned /rjh
disp = DisplayModelTextInfo(self, 'all')
x,y,w,h = self._getColumnLocation(column)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

DisplayModelTextInfo also takes a rectangle as its position argument. E.g.

right = left + width
bottom = top + height
info = displayModel.DisplayModelTextInfo(self, textInfos.Rect(left, top, right, bottom))

x,y,w,h = self._getColumnLocation(column)
start = disp._getClosestOffsetFromPoint(x,y)
end = disp._getClosestOffsetFromPoint(x+w,y+h)
# Include the whole word, even if it is white space /rjh

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See my comment above regarding initials vs mentioning the issue number

start = disp._getClosestOffsetFromPoint(x,y)
end = disp._getClosestOffsetFromPoint(x+w,y+h)
# Include the whole word, even if it is white space /rjh
wordAtEnd = disp._getWordOffsets(end)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think that this will be necessary when you create a DisplayModelTextInfo limited to the rectangle of the text.

@Robert-J-H

Copy link
Copy Markdown
Contributor Author

@LeonarddeR
Thanks for the suggestions, I will abide by them.

@LeonarddeR

LeonarddeR commented Apr 18, 2018 via email

Copy link
Copy Markdown
Collaborator

@Robert-J-H

Robert-J-H commented Apr 18, 2018 via email

Copy link
Copy Markdown
Contributor Author

@LeonarddeR LeonarddeR left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks ok to me, but I won't do an approve until I first had time to dive more deeply into the SysListView32 code.

targetColumn = self.parent._columnOrderArray[column - 1]
try:
return self._getColumnContentRaw(targetColumn)
except ArgumentError:

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you please log a debugWarning here? Like:

except ArgumentError as e:
			log.debugWarning("Could not retrieve content for column %d, %r" % (column, e))

This might be a bit obnoxious in the log though. May be log.debug would be enough here, I'm not sure. @michaelDCurran might have some thoughts about this.

@Robert-J-H

Robert-J-H commented Apr 18, 2018 via email

Copy link
Copy Markdown
Contributor Author

Try the native procedure only once for a new list.
On failure, store the handle for further  checks within this window scope.
@Robert-J-H

Copy link
Copy Markdown
Contributor Author

@LeonarddeR
The attempt of retrieving the column content is now only once performed per window since further retries would be futile.
This does consequently also log only once which is good.
The downside is that I had to add a class variable for that.
This can't be helped unless you can come up with a super-dooper-high-genius alternative. ;-)
Check also if the log message is OK.
The argument error is perhaps not of much use within this context.

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@Robert-J-H commented on 20 Apr 2018, 07:06 CEST:

The downside is that I had to add a class variable for that.

Have you considered setting a property on the parent (i.e. the list object itself)?

@Robert-J-H

Robert-J-H commented Apr 20, 2018 via email

Copy link
Copy Markdown
Contributor Author

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@Robert-J-H commented on 20 apr. 2018 16:27 CEST:

I can't see an advantage in that though.

I guess an advantage would be that we avoid using class properties. I believe that we should avoid using class properties as long as there is an alternative. Just my opinion though.

@Robert-J-H

Robert-J-H commented Apr 24, 2018 via email

Copy link
Copy Markdown
Contributor Author

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@Robert-J-H commented on 24 apr. 2018 11:30 CEST:

The parent of a list item may change, it can be a list view, combo
box, grid view, table, whatever.

We are now working with SysListView32 items. The items have window class SysListView32 and role oleacc.ROLE_SYSTEM_LISTITEM or oleacc.ROLE_SYSTEM_MENUITEM. I assume their parent is always of NVDAObject class sysListView32.List. I could be wrong though, but I"m quite sure that this is the case.

@Robert-J-H

Robert-J-H commented Apr 25, 2018 via email

Copy link
Copy Markdown
Contributor Author

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@Robert-J-H commented on 25 apr. 2018 07:58 CEST:

I've inserted a line in the changes.t2t in the English folder.
Is that the right place?

I'm afraid not. Please feel free to update your initial message in the issue to reflect your change. and revert the changes.t2t change. Updating the changes.t2t as part of pr's causes merge conflicts in most, if not all cases.

It can cause merge problems with PRs
@Robert-J-H

Robert-J-H commented Apr 26, 2018 via email

Copy link
Copy Markdown
Contributor Author

Comment thread user_docs/en/changes.t2t Outdated
== Bug Fixes ==
- NVDA no longer fails to read focused controls in the Microsoft Account sign-in screen in Settings after entering an email address. (#7997)
- NVDA no longer fails to read the page when going back to a previous page in Microsoft Edge. (#7997)
- NVDA no longer fails to read items in list views within a 64-bit application such as Tortoise SVN. (#8175)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for thinking of editing the changes file. We will actually update the changes file when we merge it to master, to prevent a ton of changes in it causing merge conflicts. Can you back this out for now?

@Robert-J-H

Copy link
Copy Markdown
Contributor Author

The change should actually be reverted with the last commit.
I assume that you will squash all the commits here into one before any merge to master, isn't it.
The removed line is kept in the very first message of this pull request, for reference sake.
Thanks for reviewing.

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@Robert-J-H commented on 26 apr. 2018 06:54 CEST:

I presume you mean the initial message of this pull request, not the
one in the issue.

Yes.

I assume that you will squash all the commits here into one before any merge to master, isn't it.

Yes, that's also the case.

LeonarddeR
LeonarddeR previously approved these changes Apr 30, 2018

@LeonarddeR LeonarddeR left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks good now, just one suggestion.

def _getColumnContent(self, column):
return self._getColumnContentRaw(self.parent._columnOrderArray[column - 1])
res = None
if self.parent._shouldEnableColumnContentRaw:

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just to make sure that this doesn't horribly crash if the parent is not a list and therefore lacks this property, could you change this to:

if getattr(self.parent, "_shouldEnableColumnContentRaw", True):

I agree that this is not very elegant, however a traceback ain't of very much elegance either.

@Robert-J-H

Robert-J-H commented May 2, 2018 via email

Copy link
Copy Markdown
Contributor Author

@LeonarddeR

Copy link
Copy Markdown
Collaborator

Thanks for changing.

@michaelDCurran, could you have an additional run over this code, just to make sure?

derekriemer
derekriemer previously approved these changes May 14, 2018
@Robert-J-H

Copy link
Copy Markdown
Contributor Author

Should be fine now, is it not.
Thanks for accepting the PR and the useful hints.

@LeonarddeR

Copy link
Copy Markdown
Collaborator

I've invested some time in the creation of a branch based on UIA, since this will also fix issues we're having with the retrieval of column locations. However, I"m afraid that that implementation would supersede your pr.

See https://github.com/babbagecom/nvda/tree/slvUIA

@Robert-J-H

Robert-J-H commented Jun 29, 2018 via email

Copy link
Copy Markdown
Contributor Author

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@Robert-J-H commented on 29 Jun 2018, 16:24 CEST:

Well, would your implementation solve the issue, that's the main question.

It probably will, as UIA deals with the part that fails on 64 bit systems wehn we do it manually. Still, there are drawbacks, as the UIA implementation seems somewhat slow.

@michaelDCurran

Copy link
Copy Markdown
Member

something is not right with this pr. It is showing many many commits on master. And more than 200 files changed. I think this pr needs to be rebased on latest master perhaps.

@Robert-J-H

Robert-J-H commented Jul 31, 2018 via email

Copy link
Copy Markdown
Contributor Author

@josephsl

Copy link
Copy Markdown
Contributor

Hi,

As this is an important pull request that was dropped from next to alpha transition, coupled with more reports on 64-bit list view issues, I think it would be best to let someone review this ASAP. But first, please try merging latest master branch so folks can review it with up to date differences.

Thanks.

@Adriani90

Copy link
Copy Markdown
Collaborator

@Robert-J-H can you merge to last master? Or did you do it already?

@Robert-J-H

Robert-J-H commented Jan 5, 2019 via email

Copy link
Copy Markdown
Contributor Author

@Robert-J-H

Robert-J-H commented Jan 5, 2019 via email

Copy link
Copy Markdown
Contributor Author

@josephsl

josephsl commented Jan 6, 2019

Copy link
Copy Markdown
Contributor

Hi,

Er, @LeonarddeR, assert came from location helper work, so can you shed some light on this? Thanks.

@josephsl

Copy link
Copy Markdown
Contributor

Hi,

Robert, are you willing to continue this work?

Thanks.

@Robert-J-H

Robert-J-H commented Aug 15, 2019 via email

Copy link
Copy Markdown
Contributor Author

@josephsl

josephsl commented Aug 15, 2019 via email

Copy link
Copy Markdown
Contributor

@dpy013

dpy013 commented Oct 31, 2019

Copy link
Copy Markdown
Contributor

hi @Robert-J-H
How is this pr progressing?
thanks

@michaelDCurran

Copy link
Copy Markdown
Member

We are going to close this pr due to inactivity. If I understand correctly, the reason that we could not fetch the column text in these 64-bit lists in the first place is a much deeper issue around pointers and virtual memory, which in some cases have caused application crashes. The higher priority solution I feel is to write some more nvdaInProcUtils functions in nvdaHelperRemote, similar to sysListView32_getGroupInfo which can get the needed info in one cross-proc call, avoiding any VirtualAllocEx / ReadProcessMemory calls etc.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

No item names for some listviews (64-bit)

9 participants