Message ID | 1309324042-22943-10-git-send-email-djkurtz@chromium.org (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Hi Daniel, > Synaptics makes (at least) two kinds of touchpad sensors: > * Older pads use a profile sensor that could only infer the location > of individual fingers based on the projection of their profiles > onto row and column sensors. > * Newer pads use an image sensor that can track true finger position > using a two-dimensional sensor grid. > > Both sensor types support an "Advanced Gesture Mode": > When multiple fingers are detected, the touchpad sends alternating > "Advanced Gesture Mode" (AGM) and "Simple Gesture Mode" (SGM) > packets. > The AGM packets have w=2, and contain reduced resolution finger data > The SGM packets have w={0,1} and contain full resolution finger data > > Profile sensors try to report the "upper" (larger y value) finger in > the SGM packet, and the lower (smaller y value) in the AGM packet. > However, due to the nature of the profile sensor, they easily get > confused when fingers cross, and can start reporting the x-coordinate > of one with the y-coordinate of the other. Thus, for profile > sensors, "semi-mt" was created, which reports a "bounding box" > created by pairing min and max coordinates of the two pairs of > reported fingers. > > Image sensors can report the actual coordinates of two of the fingers > present. This patch detects if the touchpad is an image sensor and > reports finger data using the MT-B protocol. > > NOTE: This patch only adds partial support for 2-finger gestures. > The proper interpretation of the slot contents when more than > two fingers are present is left to later patches. Also, > handling of 'number of fingers' transitions is incomplete. > > Signed-off-by: Daniel Kurtz <djkurtz@chromium.org> I guess the real question here is: do the following patches really help? Creating additional logic to band-aid yet another special case, which still does not give full MT support, seems to create more problems than it solves. If the code was needed to ensure proper five finger support to userspace, then maybe one could live with it. However, as it stands, keeping the semi-mt behavior also for the slightly better devices may not be such a bad idea, after all. _Iff_ the whole series can be formulated as true protocol B support (no special flags, please), and _iff_ it helps to use software finger tracking for less than four fingers, then please do tell, and we can add that part to the input core to simplify the synaptics implementation a bit. Thanks. Henrik -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Hi Henrik, On Tue, Jul 5, 2011 at 5:42 AM, Henrik Rydberg <rydberg@euromail.se> wrote: > Hi Daniel, > >> Synaptics makes (at least) two kinds of touchpad sensors: >> * Older pads use a profile sensor that could only infer the location >> of individual fingers based on the projection of their profiles >> onto row and column sensors. >> * Newer pads use an image sensor that can track true finger position >> using a two-dimensional sensor grid. >> >> Both sensor types support an "Advanced Gesture Mode": >> When multiple fingers are detected, the touchpad sends alternating >> "Advanced Gesture Mode" (AGM) and "Simple Gesture Mode" (SGM) >> packets. >> The AGM packets have w=2, and contain reduced resolution finger data >> The SGM packets have w={0,1} and contain full resolution finger data >> >> Profile sensors try to report the "upper" (larger y value) finger in >> the SGM packet, and the lower (smaller y value) in the AGM packet. >> However, due to the nature of the profile sensor, they easily get >> confused when fingers cross, and can start reporting the x-coordinate >> of one with the y-coordinate of the other. Thus, for profile >> sensors, "semi-mt" was created, which reports a "bounding box" >> created by pairing min and max coordinates of the two pairs of >> reported fingers. >> >> Image sensors can report the actual coordinates of two of the fingers >> present. This patch detects if the touchpad is an image sensor and >> reports finger data using the MT-B protocol. >> >> NOTE: This patch only adds partial support for 2-finger gestures. >> The proper interpretation of the slot contents when more than >> two fingers are present is left to later patches. Also, >> handling of 'number of fingers' transitions is incomplete. >> >> Signed-off-by: Daniel Kurtz <djkurtz@chromium.org> > > I guess the real question here is: do the following patches really > help? Creating additional logic to band-aid yet another special case, > which still does not give full MT support, seems to create more > problems than it solves. If the code was needed to ensure proper five > finger support to userspace, then maybe one could live with > it. However, as it stands, keeping the semi-mt behavior also for the > slightly better devices may not be such a bad idea, after all. > > _Iff_ the whole series can be formulated as true protocol B support > (no special flags, please), and _iff_ it helps to use software finger > tracking for less than four fingers, then please do tell, and we can > add that part to the input core to simplify the synaptics > implementation a bit. Image sensors and profile sensors behave differently. However, even the image sensors do not allow true MT-B, since they only report 2 fingers. Hence, it makes sense to add a property to distinguish the 3 cases. This implementation addresses the following issues: (1) Improves handling of the 2-finger case. Image sensors due allow true MT-B for two finger case. This, for example, allows detecting whether the click in a click+drag is happening in bottom right or bottom left quadrant of the pad. (2) Helps improve handling of number-of-fingers transitions. Most of the complexity of the synaptics driver comes with dealing with the complicated way that the protocol handles number-of-fingers transitions. Just ignoring them with semi-mt could cause lots of jumpy behavior as the transitions are mapped to bounding boxes whose coordinates jump around. Thus, this implementation tries to notify userspace of finger transition by 'rolling slots' when necessary. What I mean is, if the driver deduces that a given slot may not contain the same finger as a previous report, it releases it (sets its tracking_id = -1), and reestablishes the slot with a new tracking_id when it is more confident that it is now tracking a new finger. (3) Properly decode the "AGM_CONTACT" packet type. 4- and 5- finger gestures may never be supported, however, I think it is still a good idea to detect and parse these packets properly in the kernel driver, and leave policy to userspace. I'm open to alternative suggestions for ways to represent this to userspace. The idea in this patch set is to reuse the MT-B plumbing as much as possible, but use the device property to mark the fact that the interpretation of the resulting slots is somewhat different. A bare minimum patchset might do: (1) Do true MT-B for two fingers (2) Improved number-of-finger tracking for just the 2-finger case. (Keep tracking finger 1 when finger 2 is removed, and vice versa) (3) Properly parse, but don't use, AGM_CONTACT packets We can then argue about what to do with 3+ fingers :). Thanks, Daniel > > Thanks. > Henrik > -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
> > I guess the real question here is: do the following patches really > > help? Creating additional logic to band-aid yet another special case, > > which still does not give full MT support, seems to create more > > problems than it solves. If the code was needed to ensure proper five > > finger support to userspace, then maybe one could live with > > it. However, as it stands, keeping the semi-mt behavior also for the > > slightly better devices may not be such a bad idea, after all. > > > > _Iff_ the whole series can be formulated as true protocol B support > > (no special flags, please), and _iff_ it helps to use software finger > > tracking for less than four fingers, then please do tell, and we can > > add that part to the input core to simplify the synaptics > > implementation a bit. > > Image sensors and profile sensors behave differently. However, even > the image sensors do not allow true MT-B, since they only report 2 > fingers. Hence, it makes sense to add a property to distinguish the 3 > cases. The lifetime of such a solution should also be considered. > This implementation addresses the following issues: > > (1) Improves handling of the 2-finger case. Image sensors due allow > true MT-B for two finger case. This, for example, allows detecting > whether the click in a click+drag is happening in bottom right or > bottom left quadrant of the pad. In principle, this could be done within the semi-mt realm by adding a binary value to the protocol, distinguishing the diagonals of the bounding box. It would be ugly too, but at least it would be compatible with the current semi-mt effort in userspace. > (2) Helps improve handling of number-of-fingers transitions. Most > of the complexity of the synaptics driver comes with dealing with the > complicated way that the protocol handles number-of-fingers > transitions. Just ignoring them with semi-mt could cause lots of > jumpy behavior as the transitions are mapped to bounding boxes whose > coordinates jump around. Thus, this implementation tries to notify > userspace of finger transition by 'rolling slots' when necessary. If the kernel driver cannot create a smooth bounding box, which by all means is simpler than providing proper finger tracking, then there is no way this can be done in userspace either. > What I mean is, if the driver deduces that a given slot may not > contain the same finger as a previous report, it releases it (sets its > tracking_id = -1), and reestablishes the slot with a new tracking_id > when it is more confident that it is now tracking a new finger. As a general question, one might ask oneself: If the new device _really_ can track five fingers, then why does it not send enough information to recover that information? A proper tracking id would suffice. > (3) Properly decode the "AGM_CONTACT" packet type. 4- and 5- finger > gestures may never be supported, however, I think it is still a good > idea to detect and parse these packets properly in the kernel driver, > and leave policy to userspace. I'm open to alternative suggestions > for ways to represent this to userspace. The idea in this patch set > is to reuse the MT-B plumbing as much as possible, but use the device > property to mark the fact that the interpretation of the resulting > slots is somewhat different. If the data cannot be reliably utilized, I doubt anyone cares. There is a lot of hardware out there capable of tracking ten and more fingers, without the agonizing pain. > A bare minimum patchset might do: > (1) Do true MT-B for two fingers > (2) Improved number-of-finger tracking for just the 2-finger case. > (Keep tracking finger 1 when finger 2 is removed, and vice versa) In what way is this different from 1)? > (3) Properly parse, but don't use, AGM_CONTACT packets I am tempted to write something about Schrödinger's cat here... ;-) Thanks, Henrik -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Wed, Jul 6, 2011 at 3:27 AM, Henrik Rydberg <rydberg@euromail.se> wrote: >> ... >> This implementation addresses the following issues: >> >> (1) Improves handling of the 2-finger case. Image sensors due allow >> true MT-B for two finger case. This, for example, allows detecting >> whether the click in a click+drag is happening in bottom right or >> bottom left quadrant of the pad. > > In principle, this could be done within the semi-mt realm by adding a > binary value to the protocol, distinguishing the diagonals of the > bounding box. It would be ugly too, but at least it would be > compatible with the current semi-mt effort in userspace. (A) I think the "semi-mt" protocol works like this: (1) When two or more fingers are on the pad, report two MT-B slots, where: (a) slot[0] contains (x_min, y_min) of the two fingers (b) slot[1] contains (x_max, y_max) of the two fingers (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. (2) If one of the two fingers is removed, then the first slot is used to report the remaining finger, whichever it is, without changing the slot's tracking_id. (3) Advertise this behavior with the SEMI_MT device property (B) This is what the proposed T5R2 driver does: (1) When N fingers are on the pad, report N MT-B slots, where: (a) The lowest indexed active slot (tracking_id != -1) contains valid finger position data. (b) The highest indexed active slot (tracking_id != -1) contains valid finger position data. (c) Any active slots (tracking_id != -1) between these does not contain valid finger position data, these 'hidden' slots are just active to indicate that there are that many fingers on the pad. (d) Total number of fingers on the pad is always the number of active slots. (2) When fingers are removed from the pad: (a) keep reporting the fingers that are left in the same slots, with the same tracking_ids, if possible. (b) If the identities of the fingers that remain is ambiguous, invalidate all slots,then re-assign the fingers that remain to new slots, with new tracking ids. (3) Advertise this behavior with the T5R2 device property (C) A third, compromise implementation might be to do something like this: (1) When >=2 fingers are on the pad, report 2 MT-B slots, where: (a) slot[0] reports finger 1 (b) slot[1] reports finger 2 (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. (2) If 1 finger is removed, the tracking_id for its slot is invalidated; but, the finger that remains stays in its same slot with the same tracking_id. (3) Whenever the number of fingers changes from/to 3 or more fingers, both slots are always invalidated. New tracking_ids are assigned to both slots which contain the two fingers now being reported. (4) No special driver property is required for this, not even "semi-mt". It should be as pure MT-B as we can get (plus BTN_TOOL_* hack). IMHO, (C) is an improvement over (A) for two major reasons: (1) tracking the individual touches allows distinguishing a clicking finger in bottom right versus bottom left, for example. (2) It makes it possible to track the touch that remains when one of the two touches is released. The touch that remains will stay in the same slot, with the same tracking id. The tracking id of the touch that is removed will be set to -1. => This eliminates unnecessary gaps in the event stream, without introducing position jumps. This behavior occurs often when switching between 1-finger motion and 2f-scroll, or when performing 2f-click+drag gestures. Note: Tracking which fingers are left on the pad gets much more complicated with 3, 4, or 5 fingers. This is addressed more fully by the T5R2 solution, but (C), while slightly less optimal, should at least not do the wrong thing. Sorry, I find it a bit difficult to explain this clearly in writing. I guess I'll just have to submit a new patchset that shows what I mean. >> A bare minimum patchset might do: >> (1) Do true MT-B for two fingers >> (2) Improved number-of-finger tracking for just the 2-finger case. >> (Keep tracking finger 1 when finger 2 is removed, and vice versa) > > In what way is this different from 1)? > >> (3) Properly parse, but don't use, AGM_CONTACT packets The image sensor AGM mode acts different than the profile sensor. For the profile sensor, there is always one AGM for every SGM when 2 or more fingers are present. With the image sensor, there may be more 1 AGM per SGM if the number of fingers is changing - especially when there are more than 3 fingers present. This is what I meant by properly parse these packets. At least it is a form of documentation for the next poor guy who comes along and tries to figure out what in the world his trackpad is sending him. Thanks, -Daniel > > I am tempted to write something about Schrödinger's cat here... ;-) > > Thanks, > Henrik > -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On 07/06/2011 09:41 AM, Daniel Kurtz wrote: > On Wed, Jul 6, 2011 at 3:27 AM, Henrik Rydberg <rydberg@euromail.se> wrote: >>> ... >>> This implementation addresses the following issues: >>> >>> (1) Improves handling of the 2-finger case. Image sensors due allow >>> true MT-B for two finger case. This, for example, allows detecting >>> whether the click in a click+drag is happening in bottom right or >>> bottom left quadrant of the pad. >> >> In principle, this could be done within the semi-mt realm by adding a >> binary value to the protocol, distinguishing the diagonals of the >> bounding box. It would be ugly too, but at least it would be >> compatible with the current semi-mt effort in userspace. > > (A) I think the "semi-mt" protocol works like this: > (1) When two or more fingers are on the pad, report two MT-B slots, where: > (a) slot[0] contains (x_min, y_min) of the two fingers > (b) slot[1] contains (x_max, y_max) of the two fingers > (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. > (2) If one of the two fingers is removed, then the first slot is > used to report > the remaining finger, whichever it is, without changing the > slot's tracking_id. > (3) Advertise this behavior with the SEMI_MT device property > > (B) This is what the proposed T5R2 driver does: > (1) When N fingers are on the pad, report N MT-B slots, where: > (a) The lowest indexed active slot (tracking_id != -1) contains > valid finger position data. > (b) The highest indexed active slot (tracking_id != -1) contains > valid finger position data. > (c) Any active slots (tracking_id != -1) between these does not > contain valid finger position data, these 'hidden' slots are just > active to indicate that there are that many fingers on the pad. > (d) Total number of fingers on the pad is always the number of active slots. > (2) When fingers are removed from the pad: > (a) keep reporting the fingers that are left in the same slots, > with the same tracking_ids, if possible. > (b) If the identities of the fingers that remain is ambiguous, > invalidate all slots,then re-assign the fingers that remain to new > slots, with new tracking ids. > (3) Advertise this behavior with the T5R2 device property > > (C) A third, compromise implementation might be to do something like this: > (1) When >=2 fingers are on the pad, report 2 MT-B slots, where: > (a) slot[0] reports finger 1 > (b) slot[1] reports finger 2 > (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. > (2) If 1 finger is removed, the tracking_id for its slot is invalidated; > but, the finger that remains stays in its same slot with the > same tracking_id. > (3) Whenever the number of fingers changes from/to 3 or more > fingers, both slots are always invalidated. > New tracking_ids are assigned to both slots which contain the > two fingers now being reported. > (4) No special driver property is required for this, not even "semi-mt". > It should be as pure MT-B as we can get (plus BTN_TOOL_* hack). This approach seems better, but there's still an ambiguity. When we go from two to three or more fingers we get lossy. We can't tell what touches cross the transition with their data intact. I'm racking my brain trying to come up with a solution that would make sense, but I don't think there is one that works seamlessly. I think we should do what you've written above with two changes: * Use a new property (T5R2?) to fully denote how screwed up this class of devices is. * Don't roll the tracking_id on any number of touch transitions. We're already telling userspace that the number of touches is changing, so the tracking_id change is superfluous. The tracking_id of a slot should only change when we know that the touch is beginning or ending. No matter what we do, userspace will have to rely on complex heuristics for this device, which makes me wonder if these devices will really ever be handled properly... > IMHO, (C) is an improvement over (A) for two major reasons: > (1) tracking the individual touches allows distinguishing a clicking > finger in bottom right versus bottom left, for example. > (2) It makes it possible to track the touch that remains when one of > the two touches is released. > The touch that remains will stay in the same slot, with the same > tracking id. > The tracking id of the touch that is removed will be set to -1. > => This eliminates unnecessary gaps in the event stream, > without introducing position jumps. > This behavior occurs often when switching between 1-finger > motion and 2f-scroll, or when performing 2f-click+drag gestures. > > Note: Tracking which fingers are left on the pad gets much more > complicated with 3, 4, or 5 fingers. > This is addressed more fully by the T5R2 solution, but (C), while > slightly less optimal, should at least not do the wrong thing. > > Sorry, I find it a bit difficult to explain this clearly in writing. > I guess I'll just have to submit a new patchset that shows what I mean. You're not the first to be tied up trying to document Synaptics behavior :). Thanks! -- Chase -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Thu, Jul 07, 2011 at 12:41:26AM +0800, Daniel Kurtz wrote: > On Wed, Jul 6, 2011 at 3:27 AM, Henrik Rydberg <rydberg@euromail.se> wrote: > >> ... > >> This implementation addresses the following issues: > >> > >> (1) Improves handling of the 2-finger case. Image sensors due allow > >> true MT-B for two finger case. This, for example, allows detecting > >> whether the click in a click+drag is happening in bottom right or > >> bottom left quadrant of the pad. > > > > In principle, this could be done within the semi-mt realm by adding a > > binary value to the protocol, distinguishing the diagonals of the > > bounding box. It would be ugly too, but at least it would be > > compatible with the current semi-mt effort in userspace. > > (A) I think the "semi-mt" protocol works like this: > (1) When two or more fingers are on the pad, report two MT-B slots, where: > (a) slot[0] contains (x_min, y_min) of the two fingers > (b) slot[1] contains (x_max, y_max) of the two fingers > (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. > (2) If one of the two fingers is removed, then the first slot is > used to report > the remaining finger, whichever it is, without changing the > slot's tracking_id. > (3) Advertise this behavior with the SEMI_MT device property > > (B) This is what the proposed T5R2 driver does: > (1) When N fingers are on the pad, report N MT-B slots, where: > (a) The lowest indexed active slot (tracking_id != -1) contains > valid finger position data. > (b) The highest indexed active slot (tracking_id != -1) contains > valid finger position data. > (c) Any active slots (tracking_id != -1) between these does not > contain valid finger position data, these 'hidden' slots are just > active to indicate that there are that many fingers on the pad. > (d) Total number of fingers on the pad is always the number of active slots. > (2) When fingers are removed from the pad: > (a) keep reporting the fingers that are left in the same slots, > with the same tracking_ids, if possible. > (b) If the identities of the fingers that remain is ambiguous, > invalidate all slots,then re-assign the fingers that remain to new > slots, with new tracking ids. > (3) Advertise this behavior with the T5R2 device property > This is a no-go. I do not want to add TxRy or similar "properties". We have a workable semi-mt (counding box) and full mt concepts and we should present userspace with data stream that conforms either one or another. > (C) A third, compromise implementation might be to do something like this: > (1) When >=2 fingers are on the pad, report 2 MT-B slots, where: > (a) slot[0] reports finger 1 > (b) slot[1] reports finger 2 > (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. > (2) If 1 finger is removed, the tracking_id for its slot is invalidated; > but, the finger that remains stays in its same slot with the > same tracking_id. > (3) Whenever the number of fingers changes from/to 3 or more > fingers, both slots are always invalidated. > New tracking_ids are assigned to both slots which contain the > two fingers now being reported. > (4) No special driver property is required for this, not even "semi-mt". > It should be as pure MT-B as we can get (plus BTN_TOOL_* hack). > This is the best option in my opinion. We will present 2 finger position data plus extended finger count. Thanks.
> > (C) A third, compromise implementation might be to do something like this: > > (1) When >=2 fingers are on the pad, report 2 MT-B slots, where: > > (a) slot[0] reports finger 1 > > (b) slot[1] reports finger 2 > > (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. > > (2) If 1 finger is removed, the tracking_id for its slot is invalidated; > > but, the finger that remains stays in its same slot with the > > same tracking_id. > > (3) Whenever the number of fingers changes from/to 3 or more > > fingers, both slots are always invalidated. > > New tracking_ids are assigned to both slots which contain the > > two fingers now being reported. > > (4) No special driver property is required for this, not even "semi-mt". > > It should be as pure MT-B as we can get (plus BTN_TOOL_* hack). I believe there is a strong userspace assumption that BTN_TOOL_* has no meaning for real MT devices. Rightfully so, IMO. Hence, I think semi-mt needs to be used here as well. > > > > This is the best option in my opinion. We will present 2 finger position > data plus extended finger count. We never did put all the details of the bounding box coordinates in writing, so perhaps this is an opportunity to both fix that and extend usability to the case so described. The only question is whether there are applications out there which now assume min/max instead of contact positions. If anyone knows, please speak up. :-) Otherwise, I am very much for Daniel's case C, with Dmitry's modification. In short: Use the semi-MT property, and send two suitable fingers along with it. Cheers, Henrik -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Wed, Jul 06, 2011 at 08:47:59PM +0200, Henrik Rydberg wrote: > > > (C) A third, compromise implementation might be to do something like this: > > > (1) When >=2 fingers are on the pad, report 2 MT-B slots, where: > > > (a) slot[0] reports finger 1 > > > (b) slot[1] reports finger 2 > > > (c) Total number of fingers on pad is indicated by EV_KEY/BTN_TOOL_* is set. > > > (2) If 1 finger is removed, the tracking_id for its slot is invalidated; > > > but, the finger that remains stays in its same slot with the > > > same tracking_id. > > > (3) Whenever the number of fingers changes from/to 3 or more > > > fingers, both slots are always invalidated. > > > New tracking_ids are assigned to both slots which contain the > > > two fingers now being reported. > > > (4) No special driver property is required for this, not even "semi-mt". > > > It should be as pure MT-B as we can get (plus BTN_TOOL_* hack). > > I believe there is a strong userspace assumption that BTN_TOOL_* has > no meaning for real MT devices. Rightfully so, IMO. Hence, I think > semi-mt needs to be used here as well. I think we need to adjust userspace to pay attention to BTN_TOOL_* for MT-B too so that if number of slots advertised does not match BTN_TOOL_* capabilities that means that the device does not privide tracking data for all contacts. Luckily this should be backward-compatible (i.e. older userspace will ignore "extended" fingercounts, newer will pay attention to it). > > > > > > > > This is the best option in my opinion. We will present 2 finger position > > data plus extended finger count. > > We never did put all the details of the bounding box coordinates in > writing, so perhaps this is an opportunity to both fix that and extend > usability to the case so described. The only question is whether there > are applications out there which now assume min/max instead of contact > positions. If anyone knows, please speak up. :-) Otherwise, I am very > much for Daniel's case C, with Dmitry's modification. > > In short: Use the semi-MT property, and send two suitable fingers > along with it. Umm... but it is my understanding that 2 fingers will provide real tracking data, not bounding box, so why would we set semi-MT? Maybe we have different notions of what semi-MT property conveys? For me semi-MT indicates that the device provides 2 coordinates for bounding box. However if semi-MT is not set does not mean that the device provides true tracking for all contacts, but only for advertised slots. There still may be additional data transmitted. Thanks.
> > I believe there is a strong userspace assumption that BTN_TOOL_* has > > no meaning for real MT devices. Rightfully so, IMO. Hence, I think > > semi-mt needs to be used here as well. > > I think we need to adjust userspace to pay attention to BTN_TOOL_* for > MT-B too so that if number of slots advertised does not match > BTN_TOOL_* capabilities that means that the device does not privide > tracking data for all contacts. Well, it is possible, but it is a great deal more complex than just looking at what the slots contain. At least we should all be able to agree that MT-B is sufficient for any "proper" MT device. > Luckily this should be backward-compatible (i.e. older userspace will > ignore "extended" fingercounts, newer will pay attention to it). OTOH, letting semi-mt engulf all devices which requires the use of BTN_TOOL_* for finger count makes it easier to differentiate between various userspace support levels. "This app supports pure MT-B only", etc. > > > This is the best option in my opinion. We will present 2 finger position > > > data plus extended finger count. > > > > We never did put all the details of the bounding box coordinates in > > writing, so perhaps this is an opportunity to both fix that and extend > > usability to the case so described. The only question is whether there > > are applications out there which now assume min/max instead of contact > > positions. If anyone knows, please speak up. :-) Otherwise, I am very > > much for Daniel's case C, with Dmitry's modification. > > > > In short: Use the semi-MT property, and send two suitable fingers > > along with it. > > Umm... but it is my understanding that 2 fingers will provide real > tracking data, not bounding box, so why would we set semi-MT? To indicate that a) the two positions may not represent true fingers but a bounding box, and b) the contact count is determined by BTN_TOOL_*. True, there is no way to distinguish between the real-fingers and bounding-box cases here (that is why I suggested another binary value in a previous mail), but without semi-mt, there is no way to know a priori if special logic is needed for the number of fingers. > Maybe we have different notions of what semi-MT property conveys? For me > semi-MT indicates that the device provides 2 coordinates for bounding > box. However if semi-MT is not set does not mean that the device > provides true tracking for all contacts, but only for advertised slots. > There still may be additional data transmitted. Yes, it seems we do have different assumptions here. The more reason to document it further. :-) To me, it seems we do need a little bit of extra information to determine this new type of device. Thanks, Henrik -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Wed, Jul 06, 2011 at 09:31:20PM +0200, Henrik Rydberg wrote: > > > I believe there is a strong userspace assumption that BTN_TOOL_* has > > > no meaning for real MT devices. Rightfully so, IMO. Hence, I think > > > semi-mt needs to be used here as well. > > > > I think we need to adjust userspace to pay attention to BTN_TOOL_* for > > MT-B too so that if number of slots advertised does not match > > BTN_TOOL_* capabilities that means that the device does not privide > > tracking data for all contacts. > > Well, it is possible, but it is a great deal more complex than just > looking at what the slots contain. At least we should all be able to > agree that MT-B is sufficient for any "proper" MT device. > > > Luckily this should be backward-compatible (i.e. older userspace will > > ignore "extended" fingercounts, newer will pay attention to it). > > OTOH, letting semi-mt engulf all devices which requires the use of > BTN_TOOL_* for finger count makes it easier to differentiate between > various userspace support levels. "This app supports pure MT-B only", > etc. Do app writers really want to exclude semi-MT devices even though they might be usable? I can see wanting to support only MT-B protocol (as opposed to chatty MT-A) but if semi-MT stream is usable why not use it? > > > > > This is the best option in my opinion. We will present 2 finger position > > > > data plus extended finger count. > > > > > > We never did put all the details of the bounding box coordinates in > > > writing, so perhaps this is an opportunity to both fix that and extend > > > usability to the case so described. The only question is whether there > > > are applications out there which now assume min/max instead of contact > > > positions. If anyone knows, please speak up. :-) Otherwise, I am very > > > much for Daniel's case C, with Dmitry's modification. > > > > > > In short: Use the semi-MT property, and send two suitable fingers > > > along with it. > > > > Umm... but it is my understanding that 2 fingers will provide real > > tracking data, not bounding box, so why would we set semi-MT? > > To indicate that a) the two positions may not represent true fingers > but a bounding box, and b) the contact count is determined by > BTN_TOOL_*. > > True, there is no way to distinguish between the real-fingers and > bounding-box cases here And that is the problem. > (that is why I suggested another binary value > in a previous mail), but without semi-mt, there is no way to know a > priori if special logic is needed for the number of fingers. This should be pretty straightforward: num_fingers = calc_fingers_from_btn_tool(device); // via EVIOCGKEY num_slots = get_number_of_slots(device); // EVIOCGABS num_untracked_contacts = max(num_fingers - num_slots, 0); > > > Maybe we have different notions of what semi-MT property conveys? For me > > semi-MT indicates that the device provides 2 coordinates for bounding > > box. However if semi-MT is not set does not mean that the device > > provides true tracking for all contacts, but only for advertised slots. > > There still may be additional data transmitted. > > Yes, it seems we do have different assumptions here. The more reason > to document it further. :-) I'll take patches ;) > > To me, it seems we do need a little bit of extra information to > determine this new type of device. I think we already have all we need (see above). Thanks.
> This should be pretty straightforward: > > num_fingers = calc_fingers_from_btn_tool(device); // via EVIOCGKEY > num_slots = get_number_of_slots(device); // EVIOCGABS > num_untracked_contacts = max(num_fingers - num_slots, 0); Heh, I forgot we _do_ know in advance how many fingers are supported via BTN_TOOL_*. Ok, no more issues. > > > Maybe we have different notions of what semi-MT property conveys? For me > > > semi-MT indicates that the device provides 2 coordinates for bounding > > > box. However if semi-MT is not set does not mean that the device > > > provides true tracking for all contacts, but only for advertised slots. > > > There still may be additional data transmitted. > > > > Yes, it seems we do have different assumptions here. The more reason > > to document it further. :-) > > I'll take patches ;) And thou shalt receive them - some day ;-) > > To me, it seems we do need a little bit of extra information to > > determine this new type of device. > > I think we already have all we need (see above). I concur. So, to conclude: a) The improved synaptics behavior can be achieved by simply using MT-B plus BTN_TOOL_*. b) Userspace should check BTN_TOOL_* for any discrepancies between the maximum number of available slots (always two in this case) and the maximum number of fingers reported (BTN_TOOL_TRIPLETAP etc). Extra actions may then be taken to support more fingers than slots. c) The semi-mt flag is only used to signal that the two points sent via MT-B are the corners of a bounding box. Cheers, Henrik -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On 07/06/2011 01:20 PM, Henrik Rydberg wrote: >>> To me, it seems we do need a little bit of extra information to >>> determine this new type of device. >> >> I think we already have all we need (see above). > > I concur. So, to conclude: > > a) The improved synaptics behavior can be achieved by simply using > MT-B plus BTN_TOOL_*. > > b) Userspace should check BTN_TOOL_* for any discrepancies between the > maximum number of available slots (always two in this case) and the > maximum number of fingers reported (BTN_TOOL_TRIPLETAP etc). Extra > actions may then be taken to support more fingers than slots. > > c) The semi-mt flag is only used to signal that the two points sent > via MT-B are the corners of a bounding box. This isn't quite enough. If we don't set the semi-mt flag or any other new flag, then we'll have slots that become inconsistent when touches are added or removed. For example, start with two touches being tracked correctly. Now, add a touch. The second slot will now get the data of the third touch, which is in a different location. You haven't changed the tracking_id though, so it looks like the same touch. This is incorrect behavior. Or, you could change the tracking_id, but that implies that a touch was lifted and another was placed. This is also incorrect behavior. We need to tell userspace that this is a messed up device that can't accurately track touch locations across touch up/down boundaries. Once userspace sees this, it can act appropriately when it sees a transition from BTN_TOOL_DOUBLETAP to BTN_TOOL_TRIPLETAP, for example. This is how we handle transitions in the uTouch stack for semi-mt devices. Perhaps a clean implementation would be to keep semi-mt as a flag stating that there will only ever be two slots, the 0th will be the minimum (x,y) of the bounding box and the 1st will be the maximum. Then, we add a flag like NO_TOUCH_TRANSITION_TRACKING that would be set on both semi-mt and these new devices that denote the slot data may transition from one physical touchpoint to another when the number of touches changes. We could leave this up to userspace and have it detect a NO_TOUCH_TRANSITION_TRACKING device based on the fact that the max slots is less than the max fingers, but I would argue here that a more clear protocol is a better protocol. -- Chase -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Wed, Jul 06, 2011 at 02:22:53PM -0700, Chase Douglas wrote: > On 07/06/2011 01:20 PM, Henrik Rydberg wrote: > >>> To me, it seems we do need a little bit of extra information to > >>> determine this new type of device. > >> > >> I think we already have all we need (see above). > > > > I concur. So, to conclude: > > > > a) The improved synaptics behavior can be achieved by simply using > > MT-B plus BTN_TOOL_*. > > > > b) Userspace should check BTN_TOOL_* for any discrepancies between the > > maximum number of available slots (always two in this case) and the > > maximum number of fingers reported (BTN_TOOL_TRIPLETAP etc). Extra > > actions may then be taken to support more fingers than slots. > > > > c) The semi-mt flag is only used to signal that the two points sent > > via MT-B are the corners of a bounding box. > > This isn't quite enough. If we don't set the semi-mt flag or any other > new flag, then we'll have slots that become inconsistent when touches > are added or removed. For example, start with two touches being tracked > correctly. Now, add a touch. The second slot will now get the data of > the third touch, which is in a different location. You haven't changed > the tracking_id though, so it looks like the same touch. This is > incorrect behavior. Or, you could change the tracking_id, but that > implies that a touch was lifted and another was placed. This is also > incorrect behavior. The tracking ID needs to be changed as we start trackign and reporting new touch. We could see that the old touch was not removed from the fact that total number of finger reported increased. > > We need to tell userspace that this is a messed up device that can't > accurately track touch locations across touch up/down boundaries. Once > userspace sees this, it can act appropriately when it sees a transition > from BTN_TOOL_DOUBLETAP to BTN_TOOL_TRIPLETAP, for example. This is how > we handle transitions in the uTouch stack for semi-mt devices. > > Perhaps a clean implementation would be to keep semi-mt as a flag > stating that there will only ever be two slots, the 0th will be the > minimum (x,y) of the bounding box and the 1st will be the maximum. Then, > we add a flag like NO_TOUCH_TRANSITION_TRACKING that would be set on > both semi-mt and these new devices that denote the slot data may > transition from one physical touchpoint to another when the number of > touches changes. > > We could leave this up to userspace and have it detect a > NO_TOUCH_TRANSITION_TRACKING device based on the fact that the max slots > is less than the max fingers, but I would argue here that a more clear > protocol is a better protocol. I'll ask this - how much realistically do we care about 3+ finger transitions in context of these particular devices? This is a touchpad so as long as basic 2 finger gestures work (zoom, pinch, 2-finger scroll) with Synaptics X driver we should be fine. I do not want to add all kinds of custom flags to the protocol to deal with this generation of touchpads. It sounds to me like latest generation of Synaptocs protocol is a dud and hopefully they will fix it to something more flexible in the next generationof chips... Thanks.
On 07/06/2011 02:36 PM, Dmitry Torokhov wrote: > On Wed, Jul 06, 2011 at 02:22:53PM -0700, Chase Douglas wrote: >> On 07/06/2011 01:20 PM, Henrik Rydberg wrote: >>>>> To me, it seems we do need a little bit of extra information to >>>>> determine this new type of device. >>>> >>>> I think we already have all we need (see above). >>> >>> I concur. So, to conclude: >>> >>> a) The improved synaptics behavior can be achieved by simply using >>> MT-B plus BTN_TOOL_*. >>> >>> b) Userspace should check BTN_TOOL_* for any discrepancies between the >>> maximum number of available slots (always two in this case) and the >>> maximum number of fingers reported (BTN_TOOL_TRIPLETAP etc). Extra >>> actions may then be taken to support more fingers than slots. >>> >>> c) The semi-mt flag is only used to signal that the two points sent >>> via MT-B are the corners of a bounding box. >> >> This isn't quite enough. If we don't set the semi-mt flag or any other >> new flag, then we'll have slots that become inconsistent when touches >> are added or removed. For example, start with two touches being tracked >> correctly. Now, add a touch. The second slot will now get the data of >> the third touch, which is in a different location. You haven't changed >> the tracking_id though, so it looks like the same touch. This is >> incorrect behavior. Or, you could change the tracking_id, but that >> implies that a touch was lifted and another was placed. This is also >> incorrect behavior. > > The tracking ID needs to be changed as we start trackign and reporting > new touch. We could see that the old touch was not removed from the fact > that total number of finger reported increased. The evdev protocol is discrete, not continuous, so it's theoretically possible that one touch could end at the same time that another begins. IIRC, the time resolution of some MT devices makes this completely possible, perhaps to the point that it would be trival to make this happen in a few seconds of trying. I think the MT-B protocol has only ever used tracking_id for signalling touch begin and touch end, where the id goes from -1 to something else and vice versa. Maybe the protocol could be "extended" by saying that a transition from one valid id to another means there is inconsistent touch state, but the old touch hasn't necessarily ended and the new touch hasn't necessarily started at this point in time. I'm not sure this is any easier than flagging these as bad devices because now we need to watch tracking ID changes on top of touch count changes. From someone who has attempted to implement semi-mt in X synaptics, adding more complexity here should be avoided at all cost :). >> We need to tell userspace that this is a messed up device that can't >> accurately track touch locations across touch up/down boundaries. Once >> userspace sees this, it can act appropriately when it sees a transition >> from BTN_TOOL_DOUBLETAP to BTN_TOOL_TRIPLETAP, for example. This is how >> we handle transitions in the uTouch stack for semi-mt devices. >> >> Perhaps a clean implementation would be to keep semi-mt as a flag >> stating that there will only ever be two slots, the 0th will be the >> minimum (x,y) of the bounding box and the 1st will be the maximum. Then, >> we add a flag like NO_TOUCH_TRANSITION_TRACKING that would be set on >> both semi-mt and these new devices that denote the slot data may >> transition from one physical touchpoint to another when the number of >> touches changes. >> >> We could leave this up to userspace and have it detect a >> NO_TOUCH_TRANSITION_TRACKING device based on the fact that the max slots >> is less than the max fingers, but I would argue here that a more clear >> protocol is a better protocol. > > I'll ask this - how much realistically do we care about 3+ finger > transitions in context of these particular devices? This is a touchpad > so as long as basic 2 finger gestures work (zoom, pinch, 2-finger > scroll) with Synaptics X driver we should be fine. I do not want to add > all kinds of custom flags to the protocol to deal with this generation > of touchpads. I've given up on trying to send semi-mt data through the proposed XInput 2.1 multitouch protocol. I think the best option is to send all this data as valuators of a single touch (a touch and not a traditional pointer event due to the multitouch/gesture semantics). Thus, we should be focusing on what is possible in the gesture realm since we have thrown full multiouch out the window for these devices. With these devices we can support one touch drag, two touch pinch, rotate, and zoom, and 1-5 touch tap. For these to work, we need to know the number of touches at any given time, the locations of the two touches when only two touches are active, and some representative location for the 1 and 3-5 touch cases. I am sitting here writing possible solutions trying to come up with sane ways to handle all this, but every 5 minutes I erase what I came up with and start over because you only see the problems once you've analysed every scenario. I can't see any way to cater for these devices aside from: handle them as single touch because they suck, or something similar to what has been described in the past few hours. > It sounds to me like latest generation of Synaptocs protocol is a dud > and hopefully they will fix it to something more flexible in the next > generationof chips... We can only hope. In the meantime, it looks like Google is pushing to use these devices on reference designs for Chrome OS, and big vendors like Dell are perfectly happy to ship Ubuntu with the 100 times worse (because we don't know their protocol) ALPS devices. Waiting for sanity to win out seems like a lost cause to me :(. -- Chase -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
> The evdev protocol is discrete, not continuous, so it's theoretically > possible that one touch could end at the same time that another begins. > IIRC, the time resolution of some MT devices makes this completely > possible, perhaps to the point that it would be trival to make this > happen in a few seconds of trying. > > I think the MT-B protocol has only ever used tracking_id for signalling > touch begin and touch end, where the id goes from -1 to something else > and vice versa. Maybe the protocol could be "extended" by saying that a > transition from one valid id to another means there is inconsistent > touch state, but the old touch hasn't necessarily ended and the new > touch hasn't necessarily started at this point in time. The in-flight change of tracking id is actually part of the design; it makes the protocol independent of sample rate. If a particular tracking id is no longer found in any slot, that touch has ended. > I'm not sure this is any easier than flagging these as bad devices > because now we need to watch tracking ID changes on top of touch count > changes. From someone who has attempted to implement semi-mt in X > synaptics, adding more complexity here should be avoided at all cost :). The information available in the proposition suffices to determine what the device is. Surely the method of transferring that information will not have any impact on the extra code required. > > I'll ask this - how much realistically do we care about 3+ finger > > transitions in context of these particular devices? This is a touchpad > > so as long as basic 2 finger gestures work (zoom, pinch, 2-finger > > scroll) with Synaptics X driver we should be fine. I do not want to add > > all kinds of custom flags to the protocol to deal with this generation > > of touchpads. > > I've given up on trying to send semi-mt data through the proposed XInput > 2.1 multitouch protocol. I think the best option is to send all this > data as valuators of a single touch (a touch and not a traditional > pointer event due to the multitouch/gesture semantics). Thus, we should > be focusing on what is possible in the gesture realm since we have > thrown full multiouch out the window for these devices. > > With these devices we can support one touch drag, two touch pinch, > rotate, and zoom, and 1-5 touch tap. For these to work, we need to know > the number of touches at any given time, the locations of the two > touches when only two touches are active, and some representative > location for the 1 and 3-5 touch cases. Right, and we do, so there is no problem there, is there? > I am sitting here writing possible solutions trying to come up with sane > ways to handle all this, but every 5 minutes I erase what I came up with > and start over because you only see the problems once you've analysed > every scenario. I can't see any way to cater for these devices aside > from: handle them as single touch because they suck, or something > similar to what has been described in the past few hours. > > > It sounds to me like latest generation of Synaptocs protocol is a dud > > and hopefully they will fix it to something more flexible in the next > > generationof chips... > > We can only hope. In the meantime, it looks like Google is pushing to > use these devices on reference designs for Chrome OS, and big vendors > like Dell are perfectly happy to ship Ubuntu with the 100 times worse > (because we don't know their protocol) ALPS devices. Waiting for sanity > to win out seems like a lost cause to me :(. Let us bide our time and see. Cheers, Henrik -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On 07/06/2011 03:35 PM, Henrik Rydberg wrote: >> The evdev protocol is discrete, not continuous, so it's theoretically >> possible that one touch could end at the same time that another begins. >> IIRC, the time resolution of some MT devices makes this completely >> possible, perhaps to the point that it would be trival to make this >> happen in a few seconds of trying. >> >> I think the MT-B protocol has only ever used tracking_id for signalling >> touch begin and touch end, where the id goes from -1 to something else >> and vice versa. Maybe the protocol could be "extended" by saying that a >> transition from one valid id to another means there is inconsistent >> touch state, but the old touch hasn't necessarily ended and the new >> touch hasn't necessarily started at this point in time. > > The in-flight change of tracking id is actually part of the design; it > makes the protocol independent of sample rate. If a particular > tracking id is no longer found in any slot, that touch has ended. Ok. I agree that this is the best way to handle things. It does mean that we can't just change tracking_ids when the number of touches changes, so that option is out. >> I'm not sure this is any easier than flagging these as bad devices >> because now we need to watch tracking ID changes on top of touch count >> changes. From someone who has attempted to implement semi-mt in X >> synaptics, adding more complexity here should be avoided at all cost :). > > The information available in the proposition suffices to determine > what the device is. Surely the method of transferring that information > will not have any impact on the extra code required. My (unstated) question was: is watching tracking_id transitions reasonable for noting inconsistent touch changes when the number of touches changes, or should we have a way to tell if a device is broken and we must assume touch state inconsistency when the finger count changes. Given your reply above that we cannot repurpose valid tracking_id -> valid tracking_id transitions as a means of denoting touch state inconsistency, that leaves us with the latter option. You're right that the information available from the axes is enough to tell if the device is broken (i.e. if max finger count > max slot count). Ancillary to this is the question of whether we should depend on the userspace side knowing this hidden meaning, or if we should state it up front by setting a separate flag in the properties bits. I really don't want to leave this up to userspace developers having to figure out or dive into kernel code to determine what is going on, so I'm in favor of having an explicit (documented!) property flag for these devices. Why have property bits if you aren't going to use them :). >>> I'll ask this - how much realistically do we care about 3+ finger >>> transitions in context of these particular devices? This is a touchpad >>> so as long as basic 2 finger gestures work (zoom, pinch, 2-finger >>> scroll) with Synaptics X driver we should be fine. I do not want to add >>> all kinds of custom flags to the protocol to deal with this generation >>> of touchpads. >> >> I've given up on trying to send semi-mt data through the proposed XInput >> 2.1 multitouch protocol. I think the best option is to send all this >> data as valuators of a single touch (a touch and not a traditional >> pointer event due to the multitouch/gesture semantics). Thus, we should >> be focusing on what is possible in the gesture realm since we have >> thrown full multiouch out the window for these devices. >> >> With these devices we can support one touch drag, two touch pinch, >> rotate, and zoom, and 1-5 touch tap. For these to work, we need to know >> the number of touches at any given time, the locations of the two >> touches when only two touches are active, and some representative >> location for the 1 and 3-5 touch cases. > > Right, and we do, so there is no problem there, is there? Agreed, there is no problem if we go with the assumption that for these devices the touch slot data is inconsistent on touch count changes. I am satisfied with the approach that's been laid out, the only point of contention is whether userspace must infer touch state inconsistency on touch count changes by looking at max fingers and max slots, or if we provide this detail as a device property. -- Chase -- To unsubscribe from this list: send the line "unsubscribe linux-input" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
diff --git a/drivers/input/mouse/synaptics.c b/drivers/input/mouse/synaptics.c index 0a51b0ba..2d7ac0a 100644 --- a/drivers/input/mouse/synaptics.c +++ b/drivers/input/mouse/synaptics.c @@ -286,7 +286,8 @@ static int synaptics_set_advanced_gesture_mode(struct psmouse *psmouse) static unsigned char param = 0xc8; struct synaptics_data *priv = psmouse->private; - if (!SYN_CAP_ADV_GESTURE(priv->ext_cap_0c)) + if (!(SYN_CAP_ADV_GESTURE(priv->ext_cap_0c) || + SYN_CAP_IMAGE_SENSOR(priv->ext_cap_0c))) return 0; if (psmouse_sliced_command(psmouse, SYN_QUE_MODEL)) @@ -434,7 +435,9 @@ static int synaptics_parse_hw_state(const unsigned char buf[], hw->down = ((buf[0] ^ buf[3]) & 0x02) ? 1 : 0; } - if (SYN_CAP_ADV_GESTURE(priv->ext_cap_0c) && hw->w == 2) { + if ((SYN_CAP_ADV_GESTURE(priv->ext_cap_0c) + || SYN_CAP_IMAGE_SENSOR(priv->ext_cap_0c)) + && hw->w == 2) { /* Gesture packet: (x, y, z) at half resolution */ priv->agm.x = (((buf[4] & 0x0f) << 8) | buf[1]) << 1; priv->agm.y = INVERT_Y((((buf[4] & 0xf0) << 4) @@ -519,6 +522,92 @@ static void synaptics_report_semi_mt_data(struct input_dev *dev, } } +static void synaptics_report_mt_slot(struct input_dev *dev, int slot, int state, + const struct synaptics_hw_state *sgm, + const struct synaptics_hw_state *agm) +{ + input_mt_slot(dev, slot); + switch (state) { + case SYN_SLOT_EMPTY: + input_mt_report_slot_state(dev, MT_TOOL_FINGER, false); + break; + case SYN_SLOT_SGM: + input_mt_report_slot_state(dev, MT_TOOL_FINGER, true); + input_report_abs(dev, ABS_MT_POSITION_X, sgm->x); + input_report_abs(dev, ABS_MT_POSITION_Y, sgm->y); + input_report_abs(dev, ABS_MT_PRESSURE, sgm->z); + if (sgm->w >= 4) + input_report_abs(dev, ABS_MT_TOUCH_MAJOR, sgm->w); + break; + case SYN_SLOT_AGM: + input_mt_report_slot_state(dev, MT_TOOL_FINGER, true); + input_report_abs(dev, ABS_MT_POSITION_X, agm->x); + input_report_abs(dev, ABS_MT_POSITION_Y, agm->y); + input_report_abs(dev, ABS_MT_PRESSURE, agm->z); + break; + } +} + +static void synaptics_update_slots(struct synaptics_data *priv, int count, + int sgm, int agm) +{ + int i; + + /* First, clear previous slots. */ + for (i = 0; i < SYN_TRACK_SLOT_COUNT; i++) + priv->slot[i] = SYN_SLOT_EMPTY; + + if (count < 1) + return; + priv->slot[sgm] = SYN_SLOT_SGM; + + if (count < 2) + return; + priv->slot[agm] = SYN_SLOT_AGM; +} + +static void synaptics_process_hw_state(struct synaptics_data *priv, + struct synaptics_hw_state *sgm) +{ + int new_num_fingers; + + if (sgm->z == 0) + new_num_fingers = 0; + else if (sgm->w >= 4) + new_num_fingers = 1; + else if (sgm->w == 0) + new_num_fingers = 2; + else if (sgm->w == 1) + new_num_fingers = 3; + + switch (new_num_fingers) { + case 0: + synaptics_update_slots(priv, 0, 0, 0); + break; + case 1: + synaptics_update_slots(priv, 1, 0, 0); + break; + case 2: + case 3: /* Fall-through case */ + synaptics_update_slots(priv, 2, 0, 1); + break; + } + + priv->num_fingers = new_num_fingers; +} + +static void synaptics_report_mt_data(struct psmouse *psmouse, + struct synaptics_hw_state *sgm) +{ + struct input_dev *dev = psmouse->dev; + struct synaptics_data *priv = psmouse->private; + struct synaptics_hw_state *agm = &priv->agm; + int i; + + for (i = 0; i < SYN_TRACK_SLOT_COUNT; i++) + synaptics_report_mt_slot(dev, i, priv->slot[i], sgm, agm); +} + /* * called for each full received packet from the touchpad */ @@ -534,6 +623,15 @@ static void synaptics_process_packet(struct psmouse *psmouse) if (synaptics_parse_hw_state(psmouse->packet, priv, &hw)) return; + if (SYN_CAP_IMAGE_SENSOR(priv->ext_cap_0c)) { + synaptics_process_hw_state(priv, &hw); + synaptics_report_mt_data(psmouse, &hw); + input_mt_report_pointer_emulation(dev, true); + input_report_key(dev, BTN_LEFT, hw.left); + input_sync(dev); + return; + } + if (hw.scroll) { priv->scroll += hw.scroll; @@ -705,7 +803,19 @@ static void set_input_params(struct input_dev *dev, struct synaptics_data *priv) priv->y_max ?: YMAX_NOMINAL, fuzz, 0); input_set_abs_params(dev, ABS_PRESSURE, 0, 255, 0, 0); - if (SYN_CAP_ADV_GESTURE(priv->ext_cap_0c)) { + if (SYN_CAP_IMAGE_SENSOR(priv->ext_cap_0c)) { + input_mt_init_slots(dev, SYN_TRACK_SLOT_COUNT); + input_set_abs_params(dev, ABS_MT_POSITION_X, XMIN_NOMINAL, + priv->x_max ?: XMAX_NOMINAL, fuzz, 0); + input_set_abs_params(dev, ABS_MT_POSITION_Y, YMIN_NOMINAL, + priv->y_max ?: YMAX_NOMINAL, fuzz, 0); + input_set_abs_params(dev, ABS_MT_PRESSURE, 0, 255, 0, 0); + input_set_abs_params(dev, ABS_MT_TOUCH_MAJOR, 4, 15, 0, 0); + + input_abs_set_res(dev, ABS_MT_POSITION_X, priv->x_res); + input_abs_set_res(dev, ABS_MT_POSITION_Y, priv->y_res); + + } else if (SYN_CAP_ADV_GESTURE(priv->ext_cap_0c)) { __set_bit(INPUT_PROP_SEMI_MT, dev->propbit); input_mt_init_slots(dev, 2); input_set_abs_params(dev, ABS_MT_POSITION_X, XMIN_NOMINAL, diff --git a/drivers/input/mouse/synaptics.h b/drivers/input/mouse/synaptics.h index e367239..1de2256 100644 --- a/drivers/input/mouse/synaptics.h +++ b/drivers/input/mouse/synaptics.h @@ -73,6 +73,8 @@ * 2 0x04 reduced filtering firmware does less filtering on * position data, driver should watch * for noise. + * 2 0x08 image sensor image sensor tracks 5 fingers, but only + * reports 2. */ #define SYN_CAP_ADJ_THRESHOLD(ex0c) ((ex0c) & 0x010000) #define SYN_CAP_MAX_DIMENSIONS(ex0c) ((ex0c) & 0x020000) @@ -84,6 +86,7 @@ #define SYN_CAP_CLICKPAD2BTN(ex0c) ((ex0c) & 0x000100) /* 2-button ClickPad */ #define SYN_CAP_DELUXE_LED(ex0c) ((ex0c) & 0x000200) #define SYN_CAP_REDUCED_FILTERING(ex0c) ((ex0c) & 0x000400) +#define SYN_CAP_IMAGE_SENSOR(ex0c) ((ex0c) & 0x000800) /* synaptics modes query bits */ #define SYN_MODE_ABSOLUTE(m) ((m) & (1 << 7)) @@ -113,6 +116,14 @@ /* amount to fuzz position data when touchpad reports reduced filtering */ #define SYN_REDUCED_FILTER_FUZZ 8 +/* synaptics tracking slot states */ +#define SYN_SLOT_EMPTY 0 +#define SYN_SLOT_SGM 1 +#define SYN_SLOT_AGM 2 + +/* number of tracking slots for Image Sensor firmware */ +#define SYN_TRACK_SLOT_COUNT 2 + /* * A structure to describe the state of the touchpad hardware (buttons and pad) */ @@ -148,6 +159,8 @@ struct synaptics_data { struct serio *pt_port; /* Pass-through serio port */ struct synaptics_hw_state agm; /* last AGM packet */ + int num_fingers; /* current finger count */ + int slot[SYN_TRACK_SLOT_COUNT]; /* finger slot state */ }; void synaptics_module_init(void);