All of lore.kernel.org
 help / color / mirror / Atom feed
diff for duplicates of <56965661.2010307@topic.nl>

diff --git a/a/1.txt b/N1/1.txt
index e5efc27..20213cd 100644
--- a/a/1.txt
+++ b/N1/1.txt
@@ -1,224 +1,385 @@
-77u/T24gMTMtMDEtMTYgMTQ6MjQsIEd1ZW50ZXIgUm9lY2sgd3JvdGU6Cj4gT24gMDEvMTMvMjAx
-NiAwMzowNSBBTSwgTWlrZSBMb29pam1hbnMgd3JvdGU6Cj4+IFRoaXMgYWRkcyBzdXBwb3J0IGZv
-ciB0aGUgTGluZWFyIFRlY2hub2xvZ3kgTFRDMjk5MCAgSTJDIFN5c3RlbSBNb25pdG9yLgo+PiBU
-aGUgTFRDMjk5MCBzdXBwb3J0cyBhIGNvbWJpbmF0aW9uIG9mIHZvbHRhZ2UsIGN1cnJlbnQgYW5k
-IHRlbXBlcmF0dXJlCj4+IG1vbml0b3JpbmcuIFRoaXMgZHJpdmVyIGN1cnJlbnRseSBvbmx5IHN1
-cHBvcnRzIHJlYWRpbmcgdHdvIGN1cnJlbnRzCj4+IGJ5IG1lYXN1cmluZyB0d28gZGlmZmVyZW50
-aWFsIHZvbHRhZ2VzIGFjcm9zcyBzZXJpZXMgcmVzaXN0b3JzLCBpbgo+PiBhZGRpdGlvbiB0byB0
-aGUgVmNjIHN1cHBseSB2b2x0YWdlIGFuZCBpbnRlcm5hbCB0ZW1wZXJhdHVyZS4KPj4KPj4gVGhp
-cyBpcyBzdWZmaWNpZW50IHRvIHN1cHBvcnQgdGhlIFRvcGljIE1pYW1pIFNPTSB3aGljaCB1c2Vz
-IHRoaXMgY2hpcAo+PiB0byBtb25pdG9yIHRoZSBjdXJyZW50cyBmbG93aW5nIGludG8gdGhlIEZQ
-R0EgYW5kIHRoZSBDUFUgcGFydHMuCj4+Cj4+IFNpZ25lZC1vZmYtYnk6IE1pa2UgTG9vaWptYW5z
-IDxtaWtlLmxvb2lqbWFuc0B0b3BpYy5ubD4KPgo+IE1pa2UsCj4KPiBUaGF0IGxvb2tzIG11Y2gg
-YmV0dGVyLiBDYW4geW91IHNlbmQgbWUgdGhlIG91dHB1dCBvZiBpMmNkdW1wIGZvciB0aGUgY2hp
-cCA/Cj4gVGhhdCB3b3VsZCBoZWxwIG1lIHdyaXRpbmcgbW9kdWxlIHRlc3QgY29kZSBmb3IgaXQu
-CgpJJ20ga2luZGEgaW50ZXJlc3RlZCBpbnRvIGhvdyB0aGF0IHdvdWxkIHdvcmsuCgpJJ2xsIGhh
-dmUgdG8gcmVtb3ZlIHRoZSBkcml2ZXIgZmlyc3QgdG8gZ2V0IGkyY2R1bXAgdG8gd29yayBvbiB0
-aGUgY2hpcC4gSSAKY2Fubm90IGZvcmNlIGEgZGV2aWNlIHJlbW92YWwgZnJvbSB1c2VyIHNwYWNl
-IHdoaWxlIHJ1bm5pbmcsIGNhbiBJPwpBbmQgaSBzdXBwb3NlIHlvdSB3YW50IGEgZHVtcCBvZiBh
-IGNoaXAgaW4gcnVubmluZyBzdGF0dXM/IChPbiBib290LCBhbGwgYXJlIApyZWdpc3RlcnMgYXJl
-IHNpbXBseSBzZXQgdG8gemVybykKCgo+IFRoYW5rcywKPiBHdWVudGVyCj4KPj4gLS0tCj4+IHYy
-OiBQcm9jZXNzZWQgYWxsIHJldmlldyBjb21tZW50cy4KPj4gICAgICBQdXQgY2hpcCBpbnRvIGNv
-bnRpbnVvdXMgbWVhc3VyZW1lbnQgbW9kZS4KPj4gICAgICBBZGRlZCBkdWN1bWVudGF0aW9uLgo+
-PiAgICAgIFVzZSBzdGFuZGFyZCBod21vbiBpbnRlcmZhY2VzIGFuZCBtYWNyb3MuCj4+Cj4+ICAg
-RG9jdW1lbnRhdGlvbi9od21vbi9sdGMyOTkwIHwgIDQ0ICsrKysrKysrKysrKwo+PiAgIGRyaXZl
-cnMvaHdtb24vS2NvbmZpZyAgICAgICB8ICAxNCArKysrCj4+ICAgZHJpdmVycy9od21vbi9NYWtl
-ZmlsZSAgICAgIHwgICAxICsKPj4gICBkcml2ZXJzL2h3bW9uL2x0YzI5OTAuYyAgICAgfCAxNjAK
-Pj4gKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKPj4gICA0IGZp
-bGVzIGNoYW5nZWQsIDIxOSBpbnNlcnRpb25zKCspCj4+ICAgY3JlYXRlIG1vZGUgMTAwNjQ0IERv
-Y3VtZW50YXRpb24vaHdtb24vbHRjMjk5MAo+PiAgIGNyZWF0ZSBtb2RlIDEwMDY0NCBkcml2ZXJz
-L2h3bW9uL2x0YzI5OTAuYwo+Pgo+PiBkaWZmIC0tZ2l0IGEvRG9jdW1lbnRhdGlvbi9od21vbi9s
-dGMyOTkwIGIvRG9jdW1lbnRhdGlvbi9od21vbi9sdGMyOTkwCj4+IG5ldyBmaWxlIG1vZGUgMTAw
-NjQ0Cj4+IGluZGV4IDAwMDAwMDAuLjgzOGI3NGUKPj4gLS0tIC9kZXYvbnVsbAo+PiArKysgYi9E
-b2N1bWVudGF0aW9uL2h3bW9uL2x0YzI5OTAKPj4gQEAgLTAsMCArMSw0NCBAQAo+PiArS2VybmVs
-IGRyaXZlciBsdGMyOTkwCj4+ICs9PT09PT09PT09PT09PT09PT09PT0KPj4gKwo+PiArU3VwcG9y
-dGVkIGNoaXBzOgo+PiArICAqIExpbmVhciBUZWNobm9sb2d5IExUQzI5OTAKPj4gKyAgICBQcmVm
-aXg6ICdsdGMyOTkwJwo+PiArICAgIEFkZHJlc3NlcyBzY2FubmVkOiAtCj4+ICsgICAgRGF0YXNo
-ZWV0OiBodHRwOi8vd3d3LmxpbmVhci5jb20vcHJvZHVjdC9sdGMyOTkwCj4+ICsKPj4gK0F1dGhv
-cjogTWlrZSBMb29pam1hbnMgPG1pa2UubG9vaWptYW5zQHRvcGljLm5sPgo+PiArCj4+ICsKPj4g
-K0Rlc2NyaXB0aW9uCj4+ICstLS0tLS0tLS0tLQo+PiArCj4+ICtMVEMyOTkwIGlzIGEgUXVhZCBJ
-MkMgVm9sdGFnZSwgQ3VycmVudCBhbmQgVGVtcGVyYXR1cmUgTW9uaXRvci4KPj4gK1RoZSBjaGlw
-J3MgaW5wdXRzIGNhbiBtZWFzdXJlIDQgdm9sdGFnZXMsIG9yIHR3byBpbnB1dHMgdG9nZXRoZXIg
-KDErMiBhbmQgMys0KQo+PiArY2FuIGJlIGNvbWJpbmVkIHRvIG1lYXN1cmUgYSBkaWZmZXJlbnRp
-YWwgdm9sdGFnZSwgd2hpY2ggaXMgdHlwaWNhbGx5IHVzZWQgdG8KPj4gK21lYXN1cmUgY3VycmVu
-dCB0aHJvdWdoIGEgc2VyaWVzIHJlc2lzdG9yLCBvciBhIHRlbXBlcmF0dXJlLgo+PiArCj4+ICtU
-aGlzIGRyaXZlciBjdXJyZW50bHkgdXNlcyB0aGUgMnggZGlmZmVyZW50aWFsIG1vZGUgb25seS4g
-SW4gb3JkZXIgdG8gc3VwcG9ydAo+PiArb3RoZXIgbW9kZXMsIHRoZSBkcml2ZXIgd2lsbCBuZWVk
-IHRvIGJlIGV4cGFuZGVkLgo+PiArCj4+ICsKPj4gK1VzYWdlIE5vdGVzCj4+ICstLS0tLS0tLS0t
-LQo+PiArCj4+ICtUaGlzIGRyaXZlciBkb2VzIG5vdCBwcm9iZSBmb3IgUE1CdXMgZGV2aWNlcy4g
-WW91IHdpbGwgaGF2ZSB0byBpbnN0YW50aWF0ZQo+PiArZGV2aWNlcyBleHBsaWNpdGx5Lgo+PiAr
-Cj4+ICsKPj4gK1N5c2ZzIGF0dHJpYnV0ZXMKPj4gKy0tLS0tLS0tLS0tLS0tLS0KPj4gKwo+PiAr
-VGhlICJjdXJyKl9pbnB1dCIgbWVhc3VyZW1lbnRzIGFjdHVhbGx5IHJlcG9ydCB0aGUgdm9sdGFn
-ZSBkcm9wIGFjcm9zcyB0aGUKPj4gK2lucHV0IHBpbnMgaW4gbWljcm92b2x0cy4gVGhpcyBpcyBl
-cXVpdmFsZW50IHRvIHRoZSBjdXJyZW50IHRocm91Z2ggYSAxbU9obQo+PiArc2Vuc2UgcmVzaXN0
-b3IuIERpdmlkZSB0aGUgcmVwb3J0ZWQgdmFsdWUgYnkgdGhlIGFjdHVhbCBzZW5zZSByZXNpc3Rv
-ciB2YWx1ZQo+PiAraW4gbU9obSB0byBnZXQgdGhlIGFjdHVhbCB2YWx1ZS4KPj4gKwo+PiAraW4w
-X2lucHV0ICAgICBWb2x0YWdlIGF0IFZjYyBwaW4gaW4gbWlsbGl2b2x0IChyYW5nZSAyLjVWIHRv
-IDVWKQo+PiArdGVtcDFfaW5wdXQgICBJbnRlcm5hbCBjaGlwIHRlbXBlcmF0dXJlIGluIG1pbGxp
-ZGVncmVlcyBDZWxjaXVzCj4+ICtjdXJyMV9pbnB1dCAgIEN1cnJlbnQgaW4gbUEgYWNyb3NzIHYx
-LXYyIGFzc3VtaW5nIGEgMW1PaG0gc2Vuc2UgcmVzaXN0b3IuCj4+ICtjdXJyMl9pbnB1dCAgIEN1
-cnJlbnQgaW4gbUEgYWNyb3NzIHYzLXY0IGFzc3VtaW5nIGEgMW1PaG0gc2Vuc2UgcmVzaXN0b3Iu
-Cj4+ICsKPj4gZGlmZiAtLWdpdCBhL2RyaXZlcnMvaHdtb24vS2NvbmZpZyBiL2RyaXZlcnMvaHdt
-b24vS2NvbmZpZwo+PiBpbmRleCA4MGE3M2JmLi44YTMxZDY0IDEwMDY0NAo+PiAtLS0gYS9kcml2
-ZXJzL2h3bW9uL0tjb25maWcKPj4gKysrIGIvZHJpdmVycy9od21vbi9LY29uZmlnCj4+IEBAIC02
-ODUsNiArNjg1LDIwIEBAIGNvbmZpZyBTRU5TT1JTX0xUQzI5NDUKPj4gICAgICAgICBUaGlzIGRy
-aXZlciBjYW4gYWxzbyBiZSBidWlsdCBhcyBhIG1vZHVsZS4gSWYgc28sIHRoZSBtb2R1bGUgd2ls
-bAo+PiAgICAgICAgIGJlIGNhbGxlZCBsdGMyOTQ1Lgo+Pgo+PiArY29uZmlnIFNFTlNPUlNfTFRD
-Mjk5MAo+PiArICAgIHRyaXN0YXRlICJMaW5lYXIgVGVjaG5vbG9neSBMVEMyOTkwIChjdXJyZW50
-IG1vbml0b3JpbmcgbW9kZSBvbmx5KSIKPj4gKyAgICBkZXBlbmRzIG9uIEkyQwo+PiArICAgIGhl
-bHAKPj4gKyAgICAgIElmIHlvdSBzYXkgeWVzIGhlcmUgeW91IGdldCBzdXBwb3J0IGZvciBMaW5l
-YXIgVGVjaG5vbG9neSBMVEMyOTkwCj4+ICsgICAgICBJMkMgU3lzdGVtIE1vbml0b3IuIFRoZSBM
-VEMyOTkwIHN1cHBvcnRzIGEgY29tYmluYXRpb24gb2Ygdm9sdGFnZSwKPj4gKyAgICAgIGN1cnJl
-bnQgYW5kIHRlbXBlcmF0dXJlIG1vbml0b3JpbmcsIGJ1dCBpbiBhZGRpdGlvbiB0byB0aGUgVmNj
-IHN1cHBseQo+PiArICAgICAgdm9sdGFnZSBhbmQgY2hpcCB0ZW1wZXJhdHVyZSwgdGhpcyBkcml2
-ZXIgY3VycmVudGx5IG9ubHkgc3VwcG9ydHMKPj4gKyAgICAgIHJlYWRpbmcgdHdvIGN1cnJlbnRz
-IGJ5IG1lYXN1cmluZyB0d28gZGlmZmVyZW50aWFsIHZvbHRhZ2VzIGFjcm9zcwo+PiArICAgICAg
-c2VyaWVzIHJlc2lzdG9ycy4KPj4gKwo+PiArICAgICAgVGhpcyBkcml2ZXIgY2FuIGFsc28gYmUg
-YnVpbHQgYXMgYSBtb2R1bGUuIElmIHNvLCB0aGUgbW9kdWxlIHdpbGwKPj4gKyAgICAgIGJlIGNh
-bGxlZCBsdGMyOTkwLgo+PiArCj4+ICAgY29uZmlnIFNFTlNPUlNfTFRDNDE1MQo+PiAgICAgICB0
-cmlzdGF0ZSAiTGluZWFyIFRlY2hub2xvZ3kgTFRDNDE1MSIKPj4gICAgICAgZGVwZW5kcyBvbiBJ
-MkMKPj4gZGlmZiAtLWdpdCBhL2RyaXZlcnMvaHdtb24vTWFrZWZpbGUgYi9kcml2ZXJzL2h3bW9u
-L01ha2VmaWxlCj4+IGluZGV4IDEyYTMyMzkuLmU0YmQxNWIgMTAwNjQ0Cj4+IC0tLSBhL2RyaXZl
-cnMvaHdtb24vTWFrZWZpbGUKPj4gKysrIGIvZHJpdmVycy9od21vbi9NYWtlZmlsZQo+PiBAQCAt
-MTAxLDYgKzEwMSw3IEBAIG9iai0kKENPTkZJR19TRU5TT1JTX0xNOTUyMzQpICAgICs9IGxtOTUy
-MzQubwo+PiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0xNOTUyNDEpICAgICs9IGxtOTUyNDEubwo+
-PiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0xNOTUyNDUpICAgICs9IGxtOTUyNDUubwo+PiAgIG9i
-ai0kKENPTkZJR19TRU5TT1JTX0xUQzI5NDUpICAgICs9IGx0YzI5NDUubwo+PiArb2JqLSQoQ09O
-RklHX1NFTlNPUlNfTFRDMjk5MCkgICAgKz0gbHRjMjk5MC5vCj4+ICAgb2JqLSQoQ09ORklHX1NF
-TlNPUlNfTFRDNDE1MSkgICAgKz0gbHRjNDE1MS5vCj4+ICAgb2JqLSQoQ09ORklHX1NFTlNPUlNf
-TFRDNDIxNSkgICAgKz0gbHRjNDIxNS5vCj4+ICAgb2JqLSQoQ09ORklHX1NFTlNPUlNfTFRDNDIy
-MikgICAgKz0gbHRjNDIyMi5vCj4+IGRpZmYgLS1naXQgYS9kcml2ZXJzL2h3bW9uL2x0YzI5OTAu
-YyBiL2RyaXZlcnMvaHdtb24vbHRjMjk5MC5jCj4+IG5ldyBmaWxlIG1vZGUgMTAwNjQ0Cj4+IGlu
-ZGV4IDAwMDAwMDAuLjM3MjBmZjcKPj4gLS0tIC9kZXYvbnVsbAo+PiArKysgYi9kcml2ZXJzL2h3
-bW9uL2x0YzI5OTAuYwo+PiBAQCAtMCwwICsxLDE2MCBAQAo+PiArLyoKPj4gKyAqIERyaXZlciBm
-b3IgTGluZWFyIFRlY2hub2xvZ3kgTFRDMjk5MCBwb3dlciBtb25pdG9yCj4+ICsgKgo+PiArICog
-Q29weXJpZ2h0IChDKSAyMDE0IFRvcGljIEVtYmVkZGVkIFByb2R1Y3RzCj4+ICsgKiBBdXRob3I6
-IE1pa2UgTG9vaWptYW5zIDxtaWtlLmxvb2lqbWFuc0B0b3BpYy5ubD4KPj4gKyAqCj4+ICsgKiBM
-aWNlbnNlOiBHUEx2Mgo+PiArICoKPj4gKyAqIFRoaXMgZHJpdmVyIGFzc3VtZXMgdGhlIGNoaXAg
-aXMgd2lyZWQgYXMgYSBkdWFsIGN1cnJlbnQgbW9uaXRvciwgYW5kCj4+ICsgKiByZXBvcnRzIHRo
-ZSB2b2x0YWdlIGRyb3AgYWNyb3NzIHR3byBzZXJpZXMgcmVzaXN0b3JzLiBJdCBhbHNvIHJlcG9y
-dHMKPj4gKyAqIHRoZSBjaGlwJ3MgaW50ZXJuYWwgdGVtcGVyYXR1cmUgYW5kIFZjYyBwb3dlciBz
-dXBwbHkgdm9sdGFnZS4KPj4gKyAqLwo+PiArCj4+ICsjaW5jbHVkZSA8bGludXgvZGVsYXkuaD4K
-Ck5vdCBuZWVkZWQsIHdpbGwgYmUgcmVtb3ZlZCBpbiB2MwoKPj4gKyNpbmNsdWRlIDxsaW51eC9l
-cnIuaD4KPj4gKyNpbmNsdWRlIDxsaW51eC9od21vbi5oPgo+PiArI2luY2x1ZGUgPGxpbnV4L2h3
-bW9uLXN5c2ZzLmg+Cj4+ICsjaW5jbHVkZSA8bGludXgvaTJjLmg+Cj4+ICsjaW5jbHVkZSA8bGlu
-dXgva2VybmVsLmg+Cj4+ICsjaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+Cj4+ICsjaW5jbHVkZSA8
-bGludXgvc2xhYi5oPgoKTm90IG5lZWRlZAoKPj4gKwo+PiArI2RlZmluZSBMVEMyOTkwX1NUQVRV
-UyAgICAweDAwCj4+ICsjZGVmaW5lIExUQzI5OTBfQ09OVFJPTCAgICAweDAxCj4+ICsjZGVmaW5l
-IExUQzI5OTBfVFJJR0dFUiAgICAweDAyCj4+ICsjZGVmaW5lIExUQzI5OTBfVElOVF9NU0IgICAg
-MHgwNAo+PiArI2RlZmluZSBMVEMyOTkwX1RJTlRfTFNCICAgIDB4MDUKPj4gKyNkZWZpbmUgTFRD
-Mjk5MF9WMV9NU0IgICAgMHgwNgo+PiArI2RlZmluZSBMVEMyOTkwX1YxX0xTQiAgICAweDA3Cj4+
-ICsjZGVmaW5lIExUQzI5OTBfVjJfTVNCICAgIDB4MDgKPj4gKyNkZWZpbmUgTFRDMjk5MF9WMl9M
-U0IgICAgMHgwOQo+PiArI2RlZmluZSBMVEMyOTkwX1YzX01TQiAgICAweDBBCj4+ICsjZGVmaW5l
-IExUQzI5OTBfVjNfTFNCICAgIDB4MEIKPj4gKyNkZWZpbmUgTFRDMjk5MF9WNF9NU0IgICAgMHgw
-Qwo+PiArI2RlZmluZSBMVEMyOTkwX1Y0X0xTQiAgICAweDBECj4+ICsjZGVmaW5lIExUQzI5OTBf
-VkNDX01TQiAgICAweDBFCj4+ICsjZGVmaW5lIExUQzI5OTBfVkNDX0xTQiAgICAweDBGCj4+ICsK
-Pgo+IExTQiBub3QgdXNlZC4KCkFncmVlLiBXaWxsIHJlbW92ZSB0aGVtLCBpdCdzIGNsdXR0ZXIu
-Cgo+Cj4+ICsjZGVmaW5lIExUQzI5OTBfU1RBVFVTX0JVU1kgICAgQklUKDApCj4+ICsjZGVmaW5l
-IExUQzI5OTBfU1RBVFVTX1RJTlQgICAgQklUKDEpCj4+ICsjZGVmaW5lIExUQzI5OTBfU1RBVFVT
-X1YxICAgIEJJVCgyKQo+PiArI2RlZmluZSBMVEMyOTkwX1NUQVRVU19WMiAgICBCSVQoMykKPj4g
-KyNkZWZpbmUgTFRDMjk5MF9TVEFUVVNfVjMgICAgQklUKDQpCj4+ICsjZGVmaW5lIExUQzI5OTBf
-U1RBVFVTX1Y0ICAgIEJJVCg1KQo+PiArI2RlZmluZSBMVEMyOTkwX1NUQVRVU19WQ0MgICAgQklU
-KDYpCj4+ICsKPiBObyBsb25nZXIgdXNlZCA/CgpObyBuZWVkIGZvciBzdGF0dXMgcmVhZCB3aGVu
-IGluIGNvbnRpbnVvdXMgbW9kZSwgc28gdGhleSBoYXZlIG5vIHBvaW50IGJlaW5nIGhlcmUuCgo+
-Cj4+ICsvKiBPbmx5IGRlZmluZSBjb250cm9sIHNldHRpbmdzIHdlIGFjdHVhbGx5IHVzZSAqLwo+
-Cj4gSG1tbSAuLi4gYnV0IG5vdCBhbGwgYXJlIHVzZWQuCgpJIHRoaW5rIGl0J3MgYmV0dGVyIHRv
-IHJlbW92ZSB0aGF0IGNvbW1lbnQgOikKCj4+ICsjZGVmaW5lIExUQzI5OTBfQ09OVFJPTF9LRUxW
-SU4gICAgICAgIEJJVCg3KQo+PiArI2RlZmluZSBMVEMyOTkwX0NPTlRST0xfU0lOR0xFICAgICAg
-ICBCSVQoNikKPj4gKyNkZWZpbmUgTFRDMjk5MF9DT05UUk9MX01FQVNVUkVfQUxMICAgICgweDMg
-PDwgMykKPj4gKyNkZWZpbmUgTFRDMjk5MF9DT05UUk9MX01PREVfQ1VSUkVOVCAgICAweDA2Cj4+
-ICsjZGVmaW5lIExUQzI5OTBfQ09OVFJPTF9NT0RFX1ZPTFRBR0UgICAgMHgwNwo+PiArCj4+ICsv
-KiBjb252ZXJ0IHJhdyByZWdpc3RlciB2YWx1ZSB0byBzaWduLWV4dGVuZGVkIGludGVnZXIgaW4g
-MTYtYml0IHJhbmdlICovCj4+ICtzdGF0aWMgaW50IGx0YzI5OTBfdm9sdGFnZV90b19pbnQoaW50
-IHJhdykKPj4gK3sKPj4gKyAgICBpZiAocmF3ICYgQklUKDE0KSkgewo+PiArICAgICAgICByZXR1
-cm4gLSgweDQwMDAgLSAocmF3ICYgMHgzRkZGKSkgPDwgMjsKPj4gKyAgICB9IGVsc2Ugewo+PiAr
-ICAgICAgICByZXR1cm4gKHJhdyAmIDB4M0ZGRikgPDwgMjsKPj4gKyAgICB9Cj4+ICt9Cj4+ICsK
-Pj4gKy8qIFJldHVybiB0aGUgY29udmVydGVkIHZhbHVlIGZyb20gdGhlIGdpdmVuIHJlZ2lzdGVy
-IGluIHVWIG9yIG1DICovCj4+ICtzdGF0aWMgaW50IGx0YzI5OTBfZ2V0X3ZhbHVlKHN0cnVjdCBp
-MmNfY2xpZW50ICppMmMsIHU4IGluZGV4KQo+PiArewo+PiArICAgIGludCB2YWw7Cj4+ICsgICAg
-aW50IHJlc3VsdDsKPj4gKwo+PiArICAgIHZhbCA9IGkyY19zbWJ1c19yZWFkX3dvcmRfc3dhcHBl
-ZChpMmMsIChpbmRleCA8PCAxKSArIExUQzI5OTBfVElOVF9NU0IpOwo+PiArICAgIGlmICh1bmxp
-a2VseSh2YWwgPCAwKSkKPj4gKyAgICAgICAgcmV0dXJuIHZhbDsKPj4gKwo+PiArICAgIGlmIChp
-bmRleCA9PSAwKSB7IC8qIGludGVybmFsIHRlbXAsIDAuMDYyNSBkZWdyZWVzL0xTQiwgMTMtYml0
-ICAqLwo+PiArICAgICAgICB2YWwgPSAodmFsICYgMHgxRkZGKSA8PCAzOwo+PiArICAgICAgICBy
-ZXN1bHQgPSAodmFsICogMTAwMCkgPj4gNzsKPj4gKyAgICB9IGVsc2UgaWYgKGluZGV4IDwgNSkg
-eyAvKiBWeC1WeSwgMTkuNDJ1Vi9MU0IgKi8KPj4gKyAgICAgICAgcmVzdWx0ID0gbHRjMjk5MF92
-b2x0YWdlX3RvX2ludCh2YWwpICogMTk0MiAvICg0ICogMTAwKTsKPj4gKyAgICB9IGVsc2UgeyAv
-KiBWY2MsIDMwNS4xOM68Vi9MU0IsIDIuNVYgb2Zmc2V0ICovCj4+ICsgICAgICAgIHJlc3VsdCA9
-IGx0YzI5OTBfdm9sdGFnZV90b19pbnQodmFsKSAqIDMwNTE4IC8gKDQgKiAxMDAgKiAxMDAwKTsK
-Pj4gKyAgICAgICAgcmVzdWx0ICs9IDI1MDA7Cj4+ICsgICAgfQo+PiArCj4gV2l0aCB0aGUgcmVn
-aXN0ZXIgaW4gaW5kZXggKHNlZSBiZWxvdykgdGhpcyBjb3VsZCBiZQo+Cj4gICAgICB2YWwgPSBp
-MmNfc21idXNfcmVhZF93b3JkX3N3YXBwZWQoaTJjLCBpbmRleCk7Cj4KPiAgICAgIHN3aXRjaCAo
-aW5kZXgpIHsKPiAgICAgIGNhc2UgTFRDMjk5MF9USU5UX01TQjoKPiAgICAgICAgICB2YWwgPSAo
-dmFsICYgMHgxRkZGKSA8PCAzOwo+ICAgICAgICAgIHJlc3VsdCA9ICh2YWwgKiAxMDAwKSA+PiA3
-Owo+ICAgICAgICAgIGJyZWFrOwo+ICAgICAgY2FzZSBMVEMyOTkwX1YxX01TQjoKPiAgICAgIGNh
-c2UgTFRDMjk5MF9WMl9NU0I6Cj4gICAgICAgICAgLi4uCj4gICAgICAgICAgcmVzdWx0ID0gbHRj
-Mjk5MF92b2x0YWdlX3RvX2ludCh2YWwpICogMTk0MiAvICg0ICogMTAwKTsKPiAgICAgICAgICBi
-cmVhazsKPiAgICAgIGNhc2UgTFRDMjk5MF9WQ0NfTVNCOgo+ICAgICAgICAgIHJlc3VsdCA9IGx0
-YzI5OTBfdm9sdGFnZV90b19pbnQodmFsKSAqIDMwNTE4IC8gKDQgKiAxMDAgKiAxMDAwKTsKPiAg
-ICAgICAgICByZXN1bHQgKz0gMjUwMDsKPiAgICAgICAgICBicmVhazsKPiAgICAgIGRlZmF1bHQ6
-Cj4gICAgICAgICAgcmVzdWx0ID0gMDsgICAgLyogd29uJ3QgaGFwcGVuLCBtYWtlcyBjb21waWxl
-ciBoYXBweSAqLwo+ICAgICAgICAgIGJyZWFrOwo+ICAgICAgfQo+Cj4gd2hpY2ggSSB0aGluayB3
-b3VsZCBiZSBlYXNpZXIgdG8gdW5kZXJzdGFuZC4KCkFncmVlLCBnb29kIHBvaW50LiBBbHNvIHVz
-aW5nIHRoZSByZWdpc3RlciBuYW1lcyBoZWxwcyByZWFkYWJpbGl0eS4KCj4+ICsgICAgcmV0dXJu
-IHJlc3VsdDsKPj4gK30KPj4gKwo+PiArc3RhdGljIHNzaXplX3QgbHRjMjk5MF9zaG93X3ZhbHVl
-KHN0cnVjdCBkZXZpY2UgKmRldiwKPj4gKyAgICAgICAgICAgICAgICAgIHN0cnVjdCBkZXZpY2Vf
-YXR0cmlidXRlICpkYSwgY2hhciAqYnVmKQo+PiArewo+PiArICAgIHN0cnVjdCBzZW5zb3JfZGV2
-aWNlX2F0dHJpYnV0ZSAqYXR0ciA9IHRvX3NlbnNvcl9kZXZfYXR0cihkYSk7Cj4+ICsgICAgaW50
-IHZhbHVlOwo+PiArCj4+ICsgICAgdmFsdWUgPSBsdGMyOTkwX2dldF92YWx1ZShkZXZfZ2V0X2Ry
-dmRhdGEoZGV2KSwgYXR0ci0+aW5kZXgpOwo+PiArICAgIHJldHVybiBzbnByaW50ZihidWYsIFBB
-R0VfU0laRSwgIiVkXG4iLCB2YWx1ZSk7Cj4+ICt9Cj4+ICsKPj4gK3N0YXRpYyBTRU5TT1JfREVW
-SUNFX0FUVFIodGVtcDFfaW5wdXQsIFNfSVJVR08sIGx0YzI5OTBfc2hvd192YWx1ZSwgTlVMTCwg
-MCk7Cj4+ICtzdGF0aWMgU0VOU09SX0RFVklDRV9BVFRSKGN1cnIxX2lucHV0LCBTX0lSVUdPLCBs
-dGMyOTkwX3Nob3dfdmFsdWUsIE5VTEwsIDEpOwo+PiArc3RhdGljIFNFTlNPUl9ERVZJQ0VfQVRU
-UihjdXJyMl9pbnB1dCwgU19JUlVHTywgbHRjMjk5MF9zaG93X3ZhbHVlLCBOVUxMLCAzKTsKPj4g
-K3N0YXRpYyBTRU5TT1JfREVWSUNFX0FUVFIoaW4wX2lucHV0LCBTX0lSVUdPLCBsdGMyOTkwX3No
-b3dfdmFsdWUsIE5VTEwsIDUpOwo+Cj4gQ29uc2lkZXIgcHJvdmlkaW5nIHRoZSByZWdpc3RlciBN
-U0IgaW4gaW5kZXguCj4KPiBFeGFtcGxlOgo+ICAgICAgc3RhdGljIFNFTlNPUl9ERVZJQ0VfQVRU
-Uih0ZW1wMV9pbnB1dCwgU19JUlVHTywgbHRjMjk5MF9zaG93X3ZhbHVlLCBOVUxMLAo+IExUQzI5
-OTBfVElOVF9NU0IpOwoKQWdyZWUsIGFzIGFib3ZlLgoKPj4gKwo+PiArc3RhdGljIHN0cnVjdCBh
-dHRyaWJ1dGUgKmx0YzI5OTBfYXR0cnNbXSA9IHsKPj4gKyAgICAmc2Vuc29yX2Rldl9hdHRyX3Rl
-bXAxX2lucHV0LmRldl9hdHRyLmF0dHIsCj4+ICsgICAgJnNlbnNvcl9kZXZfYXR0cl9jdXJyMV9p
-bnB1dC5kZXZfYXR0ci5hdHRyLAo+PiArICAgICZzZW5zb3JfZGV2X2F0dHJfY3VycjJfaW5wdXQu
-ZGV2X2F0dHIuYXR0ciwKPj4gKyAgICAmc2Vuc29yX2Rldl9hdHRyX2luMF9pbnB1dC5kZXZfYXR0
-ci5hdHRyLAo+PiArICAgIE5VTEwsCj4+ICt9Owo+PiArQVRUUklCVVRFX0dST1VQUyhsdGMyOTkw
-KTsKPj4gKwo+PiArc3RhdGljIGludCBsdGMyOTkwX2kyY19wcm9iZShzdHJ1Y3QgaTJjX2NsaWVu
-dCAqaTJjLAo+PiArICAgIGNvbnN0IHN0cnVjdCBpMmNfZGV2aWNlX2lkICppZCkKPgo+IFBsZWFz
-ZSBhbGlnbiBjb250aW51YXRpb24gbGluZXMgd2l0aCAnKCcuCj4KPj4gK3sKPj4gKyAgICBpbnQg
-cmV0Owo+PiArICAgIHN0cnVjdCBkZXZpY2UgKmh3bW9uX2RldjsKPj4gKwo+PiArICAgIGlmICgh
-aTJjX2NoZWNrX2Z1bmN0aW9uYWxpdHkoaTJjLT5hZGFwdGVyLCBJMkNfRlVOQ19TTUJVU19CWVRF
-X0RBVEEpKQo+Cj4gQWxzbyBuZWVkIGNhcGFiaWxpdHkgdG8gcmVhZCB3b3Jkcy4KCkd1ZXNzIHNv
-Li4uCgo+Cj4+ICsgICAgICAgIHJldHVybiAtRU5PREVWOwo+PiArCj4+ICsgICAgLyogU2V0dXAg
-Y29udGludW91cyBtb2RlLCBjdXJyZW50IG1vbml0b3IgKi8KPj4gKyAgICByZXQgPSBpMmNfc21i
-dXNfd3JpdGVfYnl0ZV9kYXRhKGkyYywgTFRDMjk5MF9DT05UUk9MLAo+PiArICAgICAgICBMVEMy
-OTkwX0NPTlRST0xfTUVBU1VSRV9BTEwgfCBMVEMyOTkwX0NPTlRST0xfTU9ERV9DVVJSRU5UKTsK
-Pj4gKyAgICBpZiAocmV0IDwgMCkgewo+PiArICAgICAgICBkZXZfZXJyKCZpMmMtPmRldiwgIkVy
-cm9yOiBGYWlsZWQgdG8gc2V0IGNvbnRyb2wgbW9kZS5cbiIpOwo+PiArICAgICAgICByZXR1cm4g
-cmV0Owo+PiArICAgIH0KPj4gKyAgICAvKiBUcmlnZ2VyIG9uY2UgdG8gc3RhcnQgY29udGludW91
-cyBjb252ZXJzaW9uICovCj4+ICsgICAgcmV0ID0gaTJjX3NtYnVzX3dyaXRlX2J5dGVfZGF0YShp
-MmMsIExUQzI5OTBfVFJJR0dFUiwgMSk7Cj4+ICsgICAgaWYgKHJldCA8IDApIHsKPj4gKyAgICAg
-ICAgZGV2X2VycigmaTJjLT5kZXYsICJFcnJvcjogRmFpbGVkIHRvIHN0YXJ0IGFxdWlzaXRpb24u
-XG4iKTsKPgo+IHMvYXF1aXNpdGlvbi9hY3F1aXNpdGlvbi8KPgo+PiArICAgICAgICByZXR1cm4g
-cmV0Owo+PiArICAgIH0KPj4gKwo+PiArICAgIGh3bW9uX2RldiA9IGRldm1faHdtb25fZGV2aWNl
-X3JlZ2lzdGVyX3dpdGhfZ3JvdXBzKCZpMmMtPmRldiwKPj4gKyAgICAgICAgICAgICAgICAgICAg
-ICAgICAgICAgICBpMmMtPm5hbWUsCj4+ICsgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAg
-aTJjLAo+PiArICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGx0YzI5OTBfZ3JvdXBzKTsK
-Pj4gKwo+PiArICAgIHJldHVybiBQVFJfRVJSX09SX1pFUk8oaHdtb25fZGV2KTsKPj4gK30KPj4g
-Kwo+PiArc3RhdGljIGNvbnN0IHN0cnVjdCBpMmNfZGV2aWNlX2lkIGx0YzI5OTBfaTJjX2lkW10g
-PSB7Cj4+ICsgICAgeyAibHRjMjk5MCIsIDAgfSwKPj4gKyAgICB7fQo+PiArfTsKPj4gK01PRFVM
-RV9ERVZJQ0VfVEFCTEUoaTJjLCBsdGMyOTkwX2kyY19pZCk7Cj4+ICsKPj4gK3N0YXRpYyBzdHJ1
-Y3QgaTJjX2RyaXZlciBsdGMyOTkwX2kyY19kcml2ZXIgPSB7Cj4+ICsgICAgLmRyaXZlciA9IHsK
-Pj4gKyAgICAgICAgLm5hbWUgPSAibHRjMjk5MCIsCj4+ICsgICAgfSwKPj4gKyAgICAucHJvYmUg
-ICAgPSBsdGMyOTkwX2kyY19wcm9iZSwKPj4gKyAgICAuaWRfdGFibGUgPSBsdGMyOTkwX2kyY19p
-ZCwKPj4gK307Cj4+ICsKPj4gK21vZHVsZV9pMmNfZHJpdmVyKGx0YzI5OTBfaTJjX2RyaXZlcik7
-Cj4+ICsKPj4gK01PRFVMRV9ERVNDUklQVElPTigiTFRDMjk5MCBTZW5zb3IgRHJpdmVyIik7Cj4+
-ICtNT0RVTEVfQVVUSE9SKCJUb3BpYyBFbWJlZGRlZCBQcm9kdWN0cyIpOwo+PiArTU9EVUxFX0xJ
-Q0VOU0UoIkdQTCB2MiIpOwo+Pgo+CgoKCktpbmQgcmVnYXJkcywKCk1pa2UgTG9vaWptYW5zClN5
-c3RlbSBFeHBlcnQKClRPUElDIEVtYmVkZGVkIFByb2R1Y3RzCkVpbmRob3ZlbnNld2VnIDMyLUMs
-IE5MLTU2ODMgS0ggQmVzdApQb3N0YnVzIDQ0MCwgTkwtNTY4MCBBSyBCZXN0ClRlbGVmb29uOiAr
-MzEgKDApIDQ5OSAzMyA2OSA3OQpFLW1haWw6IG1pa2UubG9vaWptYW5zQHRvcGljcHJvZHVjdHMu
-Y29tCldlYnNpdGU6IHd3dy50b3BpY3Byb2R1Y3RzLmNvbQoKUGxlYXNlIGNvbnNpZGVyIHRoZSBl
-bnZpcm9ubWVudCBiZWZvcmUgcHJpbnRpbmcgdGhpcyBlLW1haWwKCgoKCgoKX19fX19fX19fX19f
-X19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX18KbG0tc2Vuc29ycyBtYWlsaW5nIGxp
-c3QKbG0tc2Vuc29yc0BsbS1zZW5zb3JzLm9yZwpodHRwOi8vbGlzdHMubG0tc2Vuc29ycy5vcmcv
-bWFpbG1hbi9saXN0aW5mby9sbS1zZW5zb3Jz
+On 13-01-16 14:24, Guenter Roeck wrote:
+> On 01/13/2016 03:05 AM, Mike Looijmans wrote:
+>> This adds support for the Linear Technology LTC2990  I2C System Monitor.
+>> The LTC2990 supports a combination of voltage, current and temperature
+>> monitoring. This driver currently only supports reading two currents
+>> by measuring two differential voltages across series resistors, in
+>> addition to the Vcc supply voltage and internal temperature.
+>>
+>> This is sufficient to support the Topic Miami SOM which uses this chip
+>> to monitor the currents flowing into the FPGA and the CPU parts.
+>>
+>> Signed-off-by: Mike Looijmans <mike.looijmans@topic.nl>
+>
+> Mike,
+>
+> That looks much better. Can you send me the output of i2cdump for the chip ?
+> That would help me writing module test code for it.
+
+I'm kinda interested into how that would work.
+
+I'll have to remove the driver first to get i2cdump to work on the chip. I 
+cannot force a device removal from user space while running, can I?
+And i suppose you want a dump of a chip in running status? (On boot, all are 
+registers are simply set to zero)
+
+
+> Thanks,
+> Guenter
+>
+>> ---
+>> v2: Processed all review comments.
+>>      Put chip into continuous measurement mode.
+>>      Added ducumentation.
+>>      Use standard hwmon interfaces and macros.
+>>
+>>   Documentation/hwmon/ltc2990 |  44 ++++++++++++
+>>   drivers/hwmon/Kconfig       |  14 ++++
+>>   drivers/hwmon/Makefile      |   1 +
+>>   drivers/hwmon/ltc2990.c     | 160
+>> ++++++++++++++++++++++++++++++++++++++++++++
+>>   4 files changed, 219 insertions(+)
+>>   create mode 100644 Documentation/hwmon/ltc2990
+>>   create mode 100644 drivers/hwmon/ltc2990.c
+>>
+>> diff --git a/Documentation/hwmon/ltc2990 b/Documentation/hwmon/ltc2990
+>> new file mode 100644
+>> index 0000000..838b74e
+>> --- /dev/null
+>> +++ b/Documentation/hwmon/ltc2990
+>> @@ -0,0 +1,44 @@
+>> +Kernel driver ltc2990
+>> +=====================
+>> +
+>> +Supported chips:
+>> +  * Linear Technology LTC2990
+>> +    Prefix: 'ltc2990'
+>> +    Addresses scanned: -
+>> +    Datasheet: http://www.linear.com/product/ltc2990
+>> +
+>> +Author: Mike Looijmans <mike.looijmans@topic.nl>
+>> +
+>> +
+>> +Description
+>> +-----------
+>> +
+>> +LTC2990 is a Quad I2C Voltage, Current and Temperature Monitor.
+>> +The chip's inputs can measure 4 voltages, or two inputs together (1+2 and 3+4)
+>> +can be combined to measure a differential voltage, which is typically used to
+>> +measure current through a series resistor, or a temperature.
+>> +
+>> +This driver currently uses the 2x differential mode only. In order to support
+>> +other modes, the driver will need to be expanded.
+>> +
+>> +
+>> +Usage Notes
+>> +-----------
+>> +
+>> +This driver does not probe for PMBus devices. You will have to instantiate
+>> +devices explicitly.
+>> +
+>> +
+>> +Sysfs attributes
+>> +----------------
+>> +
+>> +The "curr*_input" measurements actually report the voltage drop across the
+>> +input pins in microvolts. This is equivalent to the current through a 1mOhm
+>> +sense resistor. Divide the reported value by the actual sense resistor value
+>> +in mOhm to get the actual value.
+>> +
+>> +in0_input     Voltage at Vcc pin in millivolt (range 2.5V to 5V)
+>> +temp1_input   Internal chip temperature in millidegrees Celcius
+>> +curr1_input   Current in mA across v1-v2 assuming a 1mOhm sense resistor.
+>> +curr2_input   Current in mA across v3-v4 assuming a 1mOhm sense resistor.
+>> +
+>> diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig
+>> index 80a73bf..8a31d64 100644
+>> --- a/drivers/hwmon/Kconfig
+>> +++ b/drivers/hwmon/Kconfig
+>> @@ -685,6 +685,20 @@ config SENSORS_LTC2945
+>>         This driver can also be built as a module. If so, the module will
+>>         be called ltc2945.
+>>
+>> +config SENSORS_LTC2990
+>> +    tristate "Linear Technology LTC2990 (current monitoring mode only)"
+>> +    depends on I2C
+>> +    help
+>> +      If you say yes here you get support for Linear Technology LTC2990
+>> +      I2C System Monitor. The LTC2990 supports a combination of voltage,
+>> +      current and temperature monitoring, but in addition to the Vcc supply
+>> +      voltage and chip temperature, this driver currently only supports
+>> +      reading two currents by measuring two differential voltages across
+>> +      series resistors.
+>> +
+>> +      This driver can also be built as a module. If so, the module will
+>> +      be called ltc2990.
+>> +
+>>   config SENSORS_LTC4151
+>>       tristate "Linear Technology LTC4151"
+>>       depends on I2C
+>> diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile
+>> index 12a3239..e4bd15b 100644
+>> --- a/drivers/hwmon/Makefile
+>> +++ b/drivers/hwmon/Makefile
+>> @@ -101,6 +101,7 @@ obj-$(CONFIG_SENSORS_LM95234)    += lm95234.o
+>>   obj-$(CONFIG_SENSORS_LM95241)    += lm95241.o
+>>   obj-$(CONFIG_SENSORS_LM95245)    += lm95245.o
+>>   obj-$(CONFIG_SENSORS_LTC2945)    += ltc2945.o
+>> +obj-$(CONFIG_SENSORS_LTC2990)    += ltc2990.o
+>>   obj-$(CONFIG_SENSORS_LTC4151)    += ltc4151.o
+>>   obj-$(CONFIG_SENSORS_LTC4215)    += ltc4215.o
+>>   obj-$(CONFIG_SENSORS_LTC4222)    += ltc4222.o
+>> diff --git a/drivers/hwmon/ltc2990.c b/drivers/hwmon/ltc2990.c
+>> new file mode 100644
+>> index 0000000..3720ff7
+>> --- /dev/null
+>> +++ b/drivers/hwmon/ltc2990.c
+>> @@ -0,0 +1,160 @@
+>> +/*
+>> + * Driver for Linear Technology LTC2990 power monitor
+>> + *
+>> + * Copyright (C) 2014 Topic Embedded Products
+>> + * Author: Mike Looijmans <mike.looijmans@topic.nl>
+>> + *
+>> + * License: GPLv2
+>> + *
+>> + * This driver assumes the chip is wired as a dual current monitor, and
+>> + * reports the voltage drop across two series resistors. It also reports
+>> + * the chip's internal temperature and Vcc power supply voltage.
+>> + */
+>> +
+>> +#include <linux/delay.h>
+
+Not needed, will be removed in v3
+
+>> +#include <linux/err.h>
+>> +#include <linux/hwmon.h>
+>> +#include <linux/hwmon-sysfs.h>
+>> +#include <linux/i2c.h>
+>> +#include <linux/kernel.h>
+>> +#include <linux/module.h>
+>> +#include <linux/slab.h>
+
+Not needed
+
+>> +
+>> +#define LTC2990_STATUS    0x00
+>> +#define LTC2990_CONTROL    0x01
+>> +#define LTC2990_TRIGGER    0x02
+>> +#define LTC2990_TINT_MSB    0x04
+>> +#define LTC2990_TINT_LSB    0x05
+>> +#define LTC2990_V1_MSB    0x06
+>> +#define LTC2990_V1_LSB    0x07
+>> +#define LTC2990_V2_MSB    0x08
+>> +#define LTC2990_V2_LSB    0x09
+>> +#define LTC2990_V3_MSB    0x0A
+>> +#define LTC2990_V3_LSB    0x0B
+>> +#define LTC2990_V4_MSB    0x0C
+>> +#define LTC2990_V4_LSB    0x0D
+>> +#define LTC2990_VCC_MSB    0x0E
+>> +#define LTC2990_VCC_LSB    0x0F
+>> +
+>
+> LSB not used.
+
+Agree. Will remove them, it's clutter.
+
+>
+>> +#define LTC2990_STATUS_BUSY    BIT(0)
+>> +#define LTC2990_STATUS_TINT    BIT(1)
+>> +#define LTC2990_STATUS_V1    BIT(2)
+>> +#define LTC2990_STATUS_V2    BIT(3)
+>> +#define LTC2990_STATUS_V3    BIT(4)
+>> +#define LTC2990_STATUS_V4    BIT(5)
+>> +#define LTC2990_STATUS_VCC    BIT(6)
+>> +
+> No longer used ?
+
+No need for status read when in continuous mode, so they have no point being here.
+
+>
+>> +/* Only define control settings we actually use */
+>
+> Hmmm ... but not all are used.
+
+I think it's better to remove that comment :)
+
+>> +#define LTC2990_CONTROL_KELVIN        BIT(7)
+>> +#define LTC2990_CONTROL_SINGLE        BIT(6)
+>> +#define LTC2990_CONTROL_MEASURE_ALL    (0x3 << 3)
+>> +#define LTC2990_CONTROL_MODE_CURRENT    0x06
+>> +#define LTC2990_CONTROL_MODE_VOLTAGE    0x07
+>> +
+>> +/* convert raw register value to sign-extended integer in 16-bit range */
+>> +static int ltc2990_voltage_to_int(int raw)
+>> +{
+>> +    if (raw & BIT(14)) {
+>> +        return -(0x4000 - (raw & 0x3FFF)) << 2;
+>> +    } else {
+>> +        return (raw & 0x3FFF) << 2;
+>> +    }
+>> +}
+>> +
+>> +/* Return the converted value from the given register in uV or mC */
+>> +static int ltc2990_get_value(struct i2c_client *i2c, u8 index)
+>> +{
+>> +    int val;
+>> +    int result;
+>> +
+>> +    val = i2c_smbus_read_word_swapped(i2c, (index << 1) + LTC2990_TINT_MSB);
+>> +    if (unlikely(val < 0))
+>> +        return val;
+>> +
+>> +    if (index == 0) { /* internal temp, 0.0625 degrees/LSB, 13-bit  */
+>> +        val = (val & 0x1FFF) << 3;
+>> +        result = (val * 1000) >> 7;
+>> +    } else if (index < 5) { /* Vx-Vy, 19.42uV/LSB */
+>> +        result = ltc2990_voltage_to_int(val) * 1942 / (4 * 100);
+>> +    } else { /* Vcc, 305.18μV/LSB, 2.5V offset */
+>> +        result = ltc2990_voltage_to_int(val) * 30518 / (4 * 100 * 1000);
+>> +        result += 2500;
+>> +    }
+>> +
+> With the register in index (see below) this could be
+>
+>      val = i2c_smbus_read_word_swapped(i2c, index);
+>
+>      switch (index) {
+>      case LTC2990_TINT_MSB:
+>          val = (val & 0x1FFF) << 3;
+>          result = (val * 1000) >> 7;
+>          break;
+>      case LTC2990_V1_MSB:
+>      case LTC2990_V2_MSB:
+>          ...
+>          result = ltc2990_voltage_to_int(val) * 1942 / (4 * 100);
+>          break;
+>      case LTC2990_VCC_MSB:
+>          result = ltc2990_voltage_to_int(val) * 30518 / (4 * 100 * 1000);
+>          result += 2500;
+>          break;
+>      default:
+>          result = 0;    /* won't happen, makes compiler happy */
+>          break;
+>      }
+>
+> which I think would be easier to understand.
+
+Agree, good point. Also using the register names helps readability.
+
+>> +    return result;
+>> +}
+>> +
+>> +static ssize_t ltc2990_show_value(struct device *dev,
+>> +                  struct device_attribute *da, char *buf)
+>> +{
+>> +    struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
+>> +    int value;
+>> +
+>> +    value = ltc2990_get_value(dev_get_drvdata(dev), attr->index);
+>> +    return snprintf(buf, PAGE_SIZE, "%d\n", value);
+>> +}
+>> +
+>> +static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, ltc2990_show_value, NULL, 0);
+>> +static SENSOR_DEVICE_ATTR(curr1_input, S_IRUGO, ltc2990_show_value, NULL, 1);
+>> +static SENSOR_DEVICE_ATTR(curr2_input, S_IRUGO, ltc2990_show_value, NULL, 3);
+>> +static SENSOR_DEVICE_ATTR(in0_input, S_IRUGO, ltc2990_show_value, NULL, 5);
+>
+> Consider providing the register MSB in index.
+>
+> Example:
+>      static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, ltc2990_show_value, NULL,
+> LTC2990_TINT_MSB);
+
+Agree, as above.
+
+>> +
+>> +static struct attribute *ltc2990_attrs[] = {
+>> +    &sensor_dev_attr_temp1_input.dev_attr.attr,
+>> +    &sensor_dev_attr_curr1_input.dev_attr.attr,
+>> +    &sensor_dev_attr_curr2_input.dev_attr.attr,
+>> +    &sensor_dev_attr_in0_input.dev_attr.attr,
+>> +    NULL,
+>> +};
+>> +ATTRIBUTE_GROUPS(ltc2990);
+>> +
+>> +static int ltc2990_i2c_probe(struct i2c_client *i2c,
+>> +    const struct i2c_device_id *id)
+>
+> Please align continuation lines with '('.
+>
+>> +{
+>> +    int ret;
+>> +    struct device *hwmon_dev;
+>> +
+>> +    if (!i2c_check_functionality(i2c->adapter, I2C_FUNC_SMBUS_BYTE_DATA))
+>
+> Also need capability to read words.
+
+Guess so...
+
+>
+>> +        return -ENODEV;
+>> +
+>> +    /* Setup continuous mode, current monitor */
+>> +    ret = i2c_smbus_write_byte_data(i2c, LTC2990_CONTROL,
+>> +        LTC2990_CONTROL_MEASURE_ALL | LTC2990_CONTROL_MODE_CURRENT);
+>> +    if (ret < 0) {
+>> +        dev_err(&i2c->dev, "Error: Failed to set control mode.\n");
+>> +        return ret;
+>> +    }
+>> +    /* Trigger once to start continuous conversion */
+>> +    ret = i2c_smbus_write_byte_data(i2c, LTC2990_TRIGGER, 1);
+>> +    if (ret < 0) {
+>> +        dev_err(&i2c->dev, "Error: Failed to start aquisition.\n");
+>
+> s/aquisition/acquisition/
+>
+>> +        return ret;
+>> +    }
+>> +
+>> +    hwmon_dev = devm_hwmon_device_register_with_groups(&i2c->dev,
+>> +                               i2c->name,
+>> +                               i2c,
+>> +                               ltc2990_groups);
+>> +
+>> +    return PTR_ERR_OR_ZERO(hwmon_dev);
+>> +}
+>> +
+>> +static const struct i2c_device_id ltc2990_i2c_id[] = {
+>> +    { "ltc2990", 0 },
+>> +    {}
+>> +};
+>> +MODULE_DEVICE_TABLE(i2c, ltc2990_i2c_id);
+>> +
+>> +static struct i2c_driver ltc2990_i2c_driver = {
+>> +    .driver = {
+>> +        .name = "ltc2990",
+>> +    },
+>> +    .probe    = ltc2990_i2c_probe,
+>> +    .id_table = ltc2990_i2c_id,
+>> +};
+>> +
+>> +module_i2c_driver(ltc2990_i2c_driver);
+>> +
+>> +MODULE_DESCRIPTION("LTC2990 Sensor Driver");
+>> +MODULE_AUTHOR("Topic Embedded Products");
+>> +MODULE_LICENSE("GPL v2");
+>>
+>
+
+
+
+Kind regards,
+
+Mike Looijmans
+System Expert
+
+TOPIC Embedded Products
+Eindhovenseweg 32-C, NL-5683 KH Best
+Postbus 440, NL-5680 AK Best
+Telefoon: +31 (0) 499 33 69 79
+E-mail: mike.looijmans@topicproducts.com
+Website: www.topicproducts.com
+
+Please consider the environment before printing this e-mail
diff --git a/a/content_digest b/N1/content_digest
index 8a7f581..a281704 100644
--- a/a/content_digest
+++ b/N1/content_digest
@@ -3,237 +3,398 @@
  "ref\01452683150-27747-1-git-send-email-mike.looijmans@topic.nl\0"
  "ref\05696500E.4090905@roeck-us.net\0"
  "From\0Mike Looijmans <mike.looijmans@topic.nl>\0"
- "Subject\0Re: [lm-sensors] [PATCH v2] hwmon: Add LTC2990 sensor driver\0"
- "Date\0Wed, 13 Jan 2016 13:51:29 +0000\0"
+ "Subject\0Re: [PATCH v2] hwmon: Add LTC2990 sensor driver\0"
+ "Date\0Wed, 13 Jan 2016 14:51:29 +0100\0"
  "To\0Guenter Roeck <linux@roeck-us.net>"
- " lm-sensors@lm-sensors.org\0"
- "Cc\0jdelvare@suse.com"
- " linux-kernel@vger.kernel.org\0"
+ " <lm-sensors@lm-sensors.org>\0"
+ "Cc\0<jdelvare@suse.com>"
+ " <linux-kernel@vger.kernel.org>\0"
  "\00:1\0"
  "b\0"
- "77u/T24gMTMtMDEtMTYgMTQ6MjQsIEd1ZW50ZXIgUm9lY2sgd3JvdGU6Cj4gT24gMDEvMTMvMjAx\n"
- "NiAwMzowNSBBTSwgTWlrZSBMb29pam1hbnMgd3JvdGU6Cj4+IFRoaXMgYWRkcyBzdXBwb3J0IGZv\n"
- "ciB0aGUgTGluZWFyIFRlY2hub2xvZ3kgTFRDMjk5MCAgSTJDIFN5c3RlbSBNb25pdG9yLgo+PiBU\n"
- "aGUgTFRDMjk5MCBzdXBwb3J0cyBhIGNvbWJpbmF0aW9uIG9mIHZvbHRhZ2UsIGN1cnJlbnQgYW5k\n"
- "IHRlbXBlcmF0dXJlCj4+IG1vbml0b3JpbmcuIFRoaXMgZHJpdmVyIGN1cnJlbnRseSBvbmx5IHN1\n"
- "cHBvcnRzIHJlYWRpbmcgdHdvIGN1cnJlbnRzCj4+IGJ5IG1lYXN1cmluZyB0d28gZGlmZmVyZW50\n"
- "aWFsIHZvbHRhZ2VzIGFjcm9zcyBzZXJpZXMgcmVzaXN0b3JzLCBpbgo+PiBhZGRpdGlvbiB0byB0\n"
- "aGUgVmNjIHN1cHBseSB2b2x0YWdlIGFuZCBpbnRlcm5hbCB0ZW1wZXJhdHVyZS4KPj4KPj4gVGhp\n"
- "cyBpcyBzdWZmaWNpZW50IHRvIHN1cHBvcnQgdGhlIFRvcGljIE1pYW1pIFNPTSB3aGljaCB1c2Vz\n"
- "IHRoaXMgY2hpcAo+PiB0byBtb25pdG9yIHRoZSBjdXJyZW50cyBmbG93aW5nIGludG8gdGhlIEZQ\n"
- "R0EgYW5kIHRoZSBDUFUgcGFydHMuCj4+Cj4+IFNpZ25lZC1vZmYtYnk6IE1pa2UgTG9vaWptYW5z\n"
- "IDxtaWtlLmxvb2lqbWFuc0B0b3BpYy5ubD4KPgo+IE1pa2UsCj4KPiBUaGF0IGxvb2tzIG11Y2gg\n"
- "YmV0dGVyLiBDYW4geW91IHNlbmQgbWUgdGhlIG91dHB1dCBvZiBpMmNkdW1wIGZvciB0aGUgY2hp\n"
- "cCA/Cj4gVGhhdCB3b3VsZCBoZWxwIG1lIHdyaXRpbmcgbW9kdWxlIHRlc3QgY29kZSBmb3IgaXQu\n"
- "CgpJJ20ga2luZGEgaW50ZXJlc3RlZCBpbnRvIGhvdyB0aGF0IHdvdWxkIHdvcmsuCgpJJ2xsIGhh\n"
- "dmUgdG8gcmVtb3ZlIHRoZSBkcml2ZXIgZmlyc3QgdG8gZ2V0IGkyY2R1bXAgdG8gd29yayBvbiB0\n"
- "aGUgY2hpcC4gSSAKY2Fubm90IGZvcmNlIGEgZGV2aWNlIHJlbW92YWwgZnJvbSB1c2VyIHNwYWNl\n"
- "IHdoaWxlIHJ1bm5pbmcsIGNhbiBJPwpBbmQgaSBzdXBwb3NlIHlvdSB3YW50IGEgZHVtcCBvZiBh\n"
- "IGNoaXAgaW4gcnVubmluZyBzdGF0dXM/IChPbiBib290LCBhbGwgYXJlIApyZWdpc3RlcnMgYXJl\n"
- "IHNpbXBseSBzZXQgdG8gemVybykKCgo+IFRoYW5rcywKPiBHdWVudGVyCj4KPj4gLS0tCj4+IHYy\n"
- "OiBQcm9jZXNzZWQgYWxsIHJldmlldyBjb21tZW50cy4KPj4gICAgICBQdXQgY2hpcCBpbnRvIGNv\n"
- "bnRpbnVvdXMgbWVhc3VyZW1lbnQgbW9kZS4KPj4gICAgICBBZGRlZCBkdWN1bWVudGF0aW9uLgo+\n"
- "PiAgICAgIFVzZSBzdGFuZGFyZCBod21vbiBpbnRlcmZhY2VzIGFuZCBtYWNyb3MuCj4+Cj4+ICAg\n"
- "RG9jdW1lbnRhdGlvbi9od21vbi9sdGMyOTkwIHwgIDQ0ICsrKysrKysrKysrKwo+PiAgIGRyaXZl\n"
- "cnMvaHdtb24vS2NvbmZpZyAgICAgICB8ICAxNCArKysrCj4+ICAgZHJpdmVycy9od21vbi9NYWtl\n"
- "ZmlsZSAgICAgIHwgICAxICsKPj4gICBkcml2ZXJzL2h3bW9uL2x0YzI5OTAuYyAgICAgfCAxNjAK\n"
- "Pj4gKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysKPj4gICA0IGZp\n"
- "bGVzIGNoYW5nZWQsIDIxOSBpbnNlcnRpb25zKCspCj4+ICAgY3JlYXRlIG1vZGUgMTAwNjQ0IERv\n"
- "Y3VtZW50YXRpb24vaHdtb24vbHRjMjk5MAo+PiAgIGNyZWF0ZSBtb2RlIDEwMDY0NCBkcml2ZXJz\n"
- "L2h3bW9uL2x0YzI5OTAuYwo+Pgo+PiBkaWZmIC0tZ2l0IGEvRG9jdW1lbnRhdGlvbi9od21vbi9s\n"
- "dGMyOTkwIGIvRG9jdW1lbnRhdGlvbi9od21vbi9sdGMyOTkwCj4+IG5ldyBmaWxlIG1vZGUgMTAw\n"
- "NjQ0Cj4+IGluZGV4IDAwMDAwMDAuLjgzOGI3NGUKPj4gLS0tIC9kZXYvbnVsbAo+PiArKysgYi9E\n"
- "b2N1bWVudGF0aW9uL2h3bW9uL2x0YzI5OTAKPj4gQEAgLTAsMCArMSw0NCBAQAo+PiArS2VybmVs\n"
- "IGRyaXZlciBsdGMyOTkwCj4+ICs9PT09PT09PT09PT09PT09PT09PT0KPj4gKwo+PiArU3VwcG9y\n"
- "dGVkIGNoaXBzOgo+PiArICAqIExpbmVhciBUZWNobm9sb2d5IExUQzI5OTAKPj4gKyAgICBQcmVm\n"
- "aXg6ICdsdGMyOTkwJwo+PiArICAgIEFkZHJlc3NlcyBzY2FubmVkOiAtCj4+ICsgICAgRGF0YXNo\n"
- "ZWV0OiBodHRwOi8vd3d3LmxpbmVhci5jb20vcHJvZHVjdC9sdGMyOTkwCj4+ICsKPj4gK0F1dGhv\n"
- "cjogTWlrZSBMb29pam1hbnMgPG1pa2UubG9vaWptYW5zQHRvcGljLm5sPgo+PiArCj4+ICsKPj4g\n"
- "K0Rlc2NyaXB0aW9uCj4+ICstLS0tLS0tLS0tLQo+PiArCj4+ICtMVEMyOTkwIGlzIGEgUXVhZCBJ\n"
- "MkMgVm9sdGFnZSwgQ3VycmVudCBhbmQgVGVtcGVyYXR1cmUgTW9uaXRvci4KPj4gK1RoZSBjaGlw\n"
- "J3MgaW5wdXRzIGNhbiBtZWFzdXJlIDQgdm9sdGFnZXMsIG9yIHR3byBpbnB1dHMgdG9nZXRoZXIg\n"
- "KDErMiBhbmQgMys0KQo+PiArY2FuIGJlIGNvbWJpbmVkIHRvIG1lYXN1cmUgYSBkaWZmZXJlbnRp\n"
- "YWwgdm9sdGFnZSwgd2hpY2ggaXMgdHlwaWNhbGx5IHVzZWQgdG8KPj4gK21lYXN1cmUgY3VycmVu\n"
- "dCB0aHJvdWdoIGEgc2VyaWVzIHJlc2lzdG9yLCBvciBhIHRlbXBlcmF0dXJlLgo+PiArCj4+ICtU\n"
- "aGlzIGRyaXZlciBjdXJyZW50bHkgdXNlcyB0aGUgMnggZGlmZmVyZW50aWFsIG1vZGUgb25seS4g\n"
- "SW4gb3JkZXIgdG8gc3VwcG9ydAo+PiArb3RoZXIgbW9kZXMsIHRoZSBkcml2ZXIgd2lsbCBuZWVk\n"
- "IHRvIGJlIGV4cGFuZGVkLgo+PiArCj4+ICsKPj4gK1VzYWdlIE5vdGVzCj4+ICstLS0tLS0tLS0t\n"
- "LQo+PiArCj4+ICtUaGlzIGRyaXZlciBkb2VzIG5vdCBwcm9iZSBmb3IgUE1CdXMgZGV2aWNlcy4g\n"
- "WW91IHdpbGwgaGF2ZSB0byBpbnN0YW50aWF0ZQo+PiArZGV2aWNlcyBleHBsaWNpdGx5Lgo+PiAr\n"
- "Cj4+ICsKPj4gK1N5c2ZzIGF0dHJpYnV0ZXMKPj4gKy0tLS0tLS0tLS0tLS0tLS0KPj4gKwo+PiAr\n"
- "VGhlICJjdXJyKl9pbnB1dCIgbWVhc3VyZW1lbnRzIGFjdHVhbGx5IHJlcG9ydCB0aGUgdm9sdGFn\n"
- "ZSBkcm9wIGFjcm9zcyB0aGUKPj4gK2lucHV0IHBpbnMgaW4gbWljcm92b2x0cy4gVGhpcyBpcyBl\n"
- "cXVpdmFsZW50IHRvIHRoZSBjdXJyZW50IHRocm91Z2ggYSAxbU9obQo+PiArc2Vuc2UgcmVzaXN0\n"
- "b3IuIERpdmlkZSB0aGUgcmVwb3J0ZWQgdmFsdWUgYnkgdGhlIGFjdHVhbCBzZW5zZSByZXNpc3Rv\n"
- "ciB2YWx1ZQo+PiAraW4gbU9obSB0byBnZXQgdGhlIGFjdHVhbCB2YWx1ZS4KPj4gKwo+PiAraW4w\n"
- "X2lucHV0ICAgICBWb2x0YWdlIGF0IFZjYyBwaW4gaW4gbWlsbGl2b2x0IChyYW5nZSAyLjVWIHRv\n"
- "IDVWKQo+PiArdGVtcDFfaW5wdXQgICBJbnRlcm5hbCBjaGlwIHRlbXBlcmF0dXJlIGluIG1pbGxp\n"
- "ZGVncmVlcyBDZWxjaXVzCj4+ICtjdXJyMV9pbnB1dCAgIEN1cnJlbnQgaW4gbUEgYWNyb3NzIHYx\n"
- "LXYyIGFzc3VtaW5nIGEgMW1PaG0gc2Vuc2UgcmVzaXN0b3IuCj4+ICtjdXJyMl9pbnB1dCAgIEN1\n"
- "cnJlbnQgaW4gbUEgYWNyb3NzIHYzLXY0IGFzc3VtaW5nIGEgMW1PaG0gc2Vuc2UgcmVzaXN0b3Iu\n"
- "Cj4+ICsKPj4gZGlmZiAtLWdpdCBhL2RyaXZlcnMvaHdtb24vS2NvbmZpZyBiL2RyaXZlcnMvaHdt\n"
- "b24vS2NvbmZpZwo+PiBpbmRleCA4MGE3M2JmLi44YTMxZDY0IDEwMDY0NAo+PiAtLS0gYS9kcml2\n"
- "ZXJzL2h3bW9uL0tjb25maWcKPj4gKysrIGIvZHJpdmVycy9od21vbi9LY29uZmlnCj4+IEBAIC02\n"
- "ODUsNiArNjg1LDIwIEBAIGNvbmZpZyBTRU5TT1JTX0xUQzI5NDUKPj4gICAgICAgICBUaGlzIGRy\n"
- "aXZlciBjYW4gYWxzbyBiZSBidWlsdCBhcyBhIG1vZHVsZS4gSWYgc28sIHRoZSBtb2R1bGUgd2ls\n"
- "bAo+PiAgICAgICAgIGJlIGNhbGxlZCBsdGMyOTQ1Lgo+Pgo+PiArY29uZmlnIFNFTlNPUlNfTFRD\n"
- "Mjk5MAo+PiArICAgIHRyaXN0YXRlICJMaW5lYXIgVGVjaG5vbG9neSBMVEMyOTkwIChjdXJyZW50\n"
- "IG1vbml0b3JpbmcgbW9kZSBvbmx5KSIKPj4gKyAgICBkZXBlbmRzIG9uIEkyQwo+PiArICAgIGhl\n"
- "bHAKPj4gKyAgICAgIElmIHlvdSBzYXkgeWVzIGhlcmUgeW91IGdldCBzdXBwb3J0IGZvciBMaW5l\n"
- "YXIgVGVjaG5vbG9neSBMVEMyOTkwCj4+ICsgICAgICBJMkMgU3lzdGVtIE1vbml0b3IuIFRoZSBM\n"
- "VEMyOTkwIHN1cHBvcnRzIGEgY29tYmluYXRpb24gb2Ygdm9sdGFnZSwKPj4gKyAgICAgIGN1cnJl\n"
- "bnQgYW5kIHRlbXBlcmF0dXJlIG1vbml0b3JpbmcsIGJ1dCBpbiBhZGRpdGlvbiB0byB0aGUgVmNj\n"
- "IHN1cHBseQo+PiArICAgICAgdm9sdGFnZSBhbmQgY2hpcCB0ZW1wZXJhdHVyZSwgdGhpcyBkcml2\n"
- "ZXIgY3VycmVudGx5IG9ubHkgc3VwcG9ydHMKPj4gKyAgICAgIHJlYWRpbmcgdHdvIGN1cnJlbnRz\n"
- "IGJ5IG1lYXN1cmluZyB0d28gZGlmZmVyZW50aWFsIHZvbHRhZ2VzIGFjcm9zcwo+PiArICAgICAg\n"
- "c2VyaWVzIHJlc2lzdG9ycy4KPj4gKwo+PiArICAgICAgVGhpcyBkcml2ZXIgY2FuIGFsc28gYmUg\n"
- "YnVpbHQgYXMgYSBtb2R1bGUuIElmIHNvLCB0aGUgbW9kdWxlIHdpbGwKPj4gKyAgICAgIGJlIGNh\n"
- "bGxlZCBsdGMyOTkwLgo+PiArCj4+ICAgY29uZmlnIFNFTlNPUlNfTFRDNDE1MQo+PiAgICAgICB0\n"
- "cmlzdGF0ZSAiTGluZWFyIFRlY2hub2xvZ3kgTFRDNDE1MSIKPj4gICAgICAgZGVwZW5kcyBvbiBJ\n"
- "MkMKPj4gZGlmZiAtLWdpdCBhL2RyaXZlcnMvaHdtb24vTWFrZWZpbGUgYi9kcml2ZXJzL2h3bW9u\n"
- "L01ha2VmaWxlCj4+IGluZGV4IDEyYTMyMzkuLmU0YmQxNWIgMTAwNjQ0Cj4+IC0tLSBhL2RyaXZl\n"
- "cnMvaHdtb24vTWFrZWZpbGUKPj4gKysrIGIvZHJpdmVycy9od21vbi9NYWtlZmlsZQo+PiBAQCAt\n"
- "MTAxLDYgKzEwMSw3IEBAIG9iai0kKENPTkZJR19TRU5TT1JTX0xNOTUyMzQpICAgICs9IGxtOTUy\n"
- "MzQubwo+PiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0xNOTUyNDEpICAgICs9IGxtOTUyNDEubwo+\n"
- "PiAgIG9iai0kKENPTkZJR19TRU5TT1JTX0xNOTUyNDUpICAgICs9IGxtOTUyNDUubwo+PiAgIG9i\n"
- "ai0kKENPTkZJR19TRU5TT1JTX0xUQzI5NDUpICAgICs9IGx0YzI5NDUubwo+PiArb2JqLSQoQ09O\n"
- "RklHX1NFTlNPUlNfTFRDMjk5MCkgICAgKz0gbHRjMjk5MC5vCj4+ICAgb2JqLSQoQ09ORklHX1NF\n"
- "TlNPUlNfTFRDNDE1MSkgICAgKz0gbHRjNDE1MS5vCj4+ICAgb2JqLSQoQ09ORklHX1NFTlNPUlNf\n"
- "TFRDNDIxNSkgICAgKz0gbHRjNDIxNS5vCj4+ICAgb2JqLSQoQ09ORklHX1NFTlNPUlNfTFRDNDIy\n"
- "MikgICAgKz0gbHRjNDIyMi5vCj4+IGRpZmYgLS1naXQgYS9kcml2ZXJzL2h3bW9uL2x0YzI5OTAu\n"
- "YyBiL2RyaXZlcnMvaHdtb24vbHRjMjk5MC5jCj4+IG5ldyBmaWxlIG1vZGUgMTAwNjQ0Cj4+IGlu\n"
- "ZGV4IDAwMDAwMDAuLjM3MjBmZjcKPj4gLS0tIC9kZXYvbnVsbAo+PiArKysgYi9kcml2ZXJzL2h3\n"
- "bW9uL2x0YzI5OTAuYwo+PiBAQCAtMCwwICsxLDE2MCBAQAo+PiArLyoKPj4gKyAqIERyaXZlciBm\n"
- "b3IgTGluZWFyIFRlY2hub2xvZ3kgTFRDMjk5MCBwb3dlciBtb25pdG9yCj4+ICsgKgo+PiArICog\n"
- "Q29weXJpZ2h0IChDKSAyMDE0IFRvcGljIEVtYmVkZGVkIFByb2R1Y3RzCj4+ICsgKiBBdXRob3I6\n"
- "IE1pa2UgTG9vaWptYW5zIDxtaWtlLmxvb2lqbWFuc0B0b3BpYy5ubD4KPj4gKyAqCj4+ICsgKiBM\n"
- "aWNlbnNlOiBHUEx2Mgo+PiArICoKPj4gKyAqIFRoaXMgZHJpdmVyIGFzc3VtZXMgdGhlIGNoaXAg\n"
- "aXMgd2lyZWQgYXMgYSBkdWFsIGN1cnJlbnQgbW9uaXRvciwgYW5kCj4+ICsgKiByZXBvcnRzIHRo\n"
- "ZSB2b2x0YWdlIGRyb3AgYWNyb3NzIHR3byBzZXJpZXMgcmVzaXN0b3JzLiBJdCBhbHNvIHJlcG9y\n"
- "dHMKPj4gKyAqIHRoZSBjaGlwJ3MgaW50ZXJuYWwgdGVtcGVyYXR1cmUgYW5kIFZjYyBwb3dlciBz\n"
- "dXBwbHkgdm9sdGFnZS4KPj4gKyAqLwo+PiArCj4+ICsjaW5jbHVkZSA8bGludXgvZGVsYXkuaD4K\n"
- "Ck5vdCBuZWVkZWQsIHdpbGwgYmUgcmVtb3ZlZCBpbiB2MwoKPj4gKyNpbmNsdWRlIDxsaW51eC9l\n"
- "cnIuaD4KPj4gKyNpbmNsdWRlIDxsaW51eC9od21vbi5oPgo+PiArI2luY2x1ZGUgPGxpbnV4L2h3\n"
- "bW9uLXN5c2ZzLmg+Cj4+ICsjaW5jbHVkZSA8bGludXgvaTJjLmg+Cj4+ICsjaW5jbHVkZSA8bGlu\n"
- "dXgva2VybmVsLmg+Cj4+ICsjaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+Cj4+ICsjaW5jbHVkZSA8\n"
- "bGludXgvc2xhYi5oPgoKTm90IG5lZWRlZAoKPj4gKwo+PiArI2RlZmluZSBMVEMyOTkwX1NUQVRV\n"
- "UyAgICAweDAwCj4+ICsjZGVmaW5lIExUQzI5OTBfQ09OVFJPTCAgICAweDAxCj4+ICsjZGVmaW5l\n"
- "IExUQzI5OTBfVFJJR0dFUiAgICAweDAyCj4+ICsjZGVmaW5lIExUQzI5OTBfVElOVF9NU0IgICAg\n"
- "MHgwNAo+PiArI2RlZmluZSBMVEMyOTkwX1RJTlRfTFNCICAgIDB4MDUKPj4gKyNkZWZpbmUgTFRD\n"
- "Mjk5MF9WMV9NU0IgICAgMHgwNgo+PiArI2RlZmluZSBMVEMyOTkwX1YxX0xTQiAgICAweDA3Cj4+\n"
- "ICsjZGVmaW5lIExUQzI5OTBfVjJfTVNCICAgIDB4MDgKPj4gKyNkZWZpbmUgTFRDMjk5MF9WMl9M\n"
- "U0IgICAgMHgwOQo+PiArI2RlZmluZSBMVEMyOTkwX1YzX01TQiAgICAweDBBCj4+ICsjZGVmaW5l\n"
- "IExUQzI5OTBfVjNfTFNCICAgIDB4MEIKPj4gKyNkZWZpbmUgTFRDMjk5MF9WNF9NU0IgICAgMHgw\n"
- "Qwo+PiArI2RlZmluZSBMVEMyOTkwX1Y0X0xTQiAgICAweDBECj4+ICsjZGVmaW5lIExUQzI5OTBf\n"
- "VkNDX01TQiAgICAweDBFCj4+ICsjZGVmaW5lIExUQzI5OTBfVkNDX0xTQiAgICAweDBGCj4+ICsK\n"
- "Pgo+IExTQiBub3QgdXNlZC4KCkFncmVlLiBXaWxsIHJlbW92ZSB0aGVtLCBpdCdzIGNsdXR0ZXIu\n"
- "Cgo+Cj4+ICsjZGVmaW5lIExUQzI5OTBfU1RBVFVTX0JVU1kgICAgQklUKDApCj4+ICsjZGVmaW5l\n"
- "IExUQzI5OTBfU1RBVFVTX1RJTlQgICAgQklUKDEpCj4+ICsjZGVmaW5lIExUQzI5OTBfU1RBVFVT\n"
- "X1YxICAgIEJJVCgyKQo+PiArI2RlZmluZSBMVEMyOTkwX1NUQVRVU19WMiAgICBCSVQoMykKPj4g\n"
- "KyNkZWZpbmUgTFRDMjk5MF9TVEFUVVNfVjMgICAgQklUKDQpCj4+ICsjZGVmaW5lIExUQzI5OTBf\n"
- "U1RBVFVTX1Y0ICAgIEJJVCg1KQo+PiArI2RlZmluZSBMVEMyOTkwX1NUQVRVU19WQ0MgICAgQklU\n"
- "KDYpCj4+ICsKPiBObyBsb25nZXIgdXNlZCA/CgpObyBuZWVkIGZvciBzdGF0dXMgcmVhZCB3aGVu\n"
- "IGluIGNvbnRpbnVvdXMgbW9kZSwgc28gdGhleSBoYXZlIG5vIHBvaW50IGJlaW5nIGhlcmUuCgo+\n"
- "Cj4+ICsvKiBPbmx5IGRlZmluZSBjb250cm9sIHNldHRpbmdzIHdlIGFjdHVhbGx5IHVzZSAqLwo+\n"
- "Cj4gSG1tbSAuLi4gYnV0IG5vdCBhbGwgYXJlIHVzZWQuCgpJIHRoaW5rIGl0J3MgYmV0dGVyIHRv\n"
- "IHJlbW92ZSB0aGF0IGNvbW1lbnQgOikKCj4+ICsjZGVmaW5lIExUQzI5OTBfQ09OVFJPTF9LRUxW\n"
- "SU4gICAgICAgIEJJVCg3KQo+PiArI2RlZmluZSBMVEMyOTkwX0NPTlRST0xfU0lOR0xFICAgICAg\n"
- "ICBCSVQoNikKPj4gKyNkZWZpbmUgTFRDMjk5MF9DT05UUk9MX01FQVNVUkVfQUxMICAgICgweDMg\n"
- "PDwgMykKPj4gKyNkZWZpbmUgTFRDMjk5MF9DT05UUk9MX01PREVfQ1VSUkVOVCAgICAweDA2Cj4+\n"
- "ICsjZGVmaW5lIExUQzI5OTBfQ09OVFJPTF9NT0RFX1ZPTFRBR0UgICAgMHgwNwo+PiArCj4+ICsv\n"
- "KiBjb252ZXJ0IHJhdyByZWdpc3RlciB2YWx1ZSB0byBzaWduLWV4dGVuZGVkIGludGVnZXIgaW4g\n"
- "MTYtYml0IHJhbmdlICovCj4+ICtzdGF0aWMgaW50IGx0YzI5OTBfdm9sdGFnZV90b19pbnQoaW50\n"
- "IHJhdykKPj4gK3sKPj4gKyAgICBpZiAocmF3ICYgQklUKDE0KSkgewo+PiArICAgICAgICByZXR1\n"
- "cm4gLSgweDQwMDAgLSAocmF3ICYgMHgzRkZGKSkgPDwgMjsKPj4gKyAgICB9IGVsc2Ugewo+PiAr\n"
- "ICAgICAgICByZXR1cm4gKHJhdyAmIDB4M0ZGRikgPDwgMjsKPj4gKyAgICB9Cj4+ICt9Cj4+ICsK\n"
- "Pj4gKy8qIFJldHVybiB0aGUgY29udmVydGVkIHZhbHVlIGZyb20gdGhlIGdpdmVuIHJlZ2lzdGVy\n"
- "IGluIHVWIG9yIG1DICovCj4+ICtzdGF0aWMgaW50IGx0YzI5OTBfZ2V0X3ZhbHVlKHN0cnVjdCBp\n"
- "MmNfY2xpZW50ICppMmMsIHU4IGluZGV4KQo+PiArewo+PiArICAgIGludCB2YWw7Cj4+ICsgICAg\n"
- "aW50IHJlc3VsdDsKPj4gKwo+PiArICAgIHZhbCA9IGkyY19zbWJ1c19yZWFkX3dvcmRfc3dhcHBl\n"
- "ZChpMmMsIChpbmRleCA8PCAxKSArIExUQzI5OTBfVElOVF9NU0IpOwo+PiArICAgIGlmICh1bmxp\n"
- "a2VseSh2YWwgPCAwKSkKPj4gKyAgICAgICAgcmV0dXJuIHZhbDsKPj4gKwo+PiArICAgIGlmIChp\n"
- "bmRleCA9PSAwKSB7IC8qIGludGVybmFsIHRlbXAsIDAuMDYyNSBkZWdyZWVzL0xTQiwgMTMtYml0\n"
- "ICAqLwo+PiArICAgICAgICB2YWwgPSAodmFsICYgMHgxRkZGKSA8PCAzOwo+PiArICAgICAgICBy\n"
- "ZXN1bHQgPSAodmFsICogMTAwMCkgPj4gNzsKPj4gKyAgICB9IGVsc2UgaWYgKGluZGV4IDwgNSkg\n"
- "eyAvKiBWeC1WeSwgMTkuNDJ1Vi9MU0IgKi8KPj4gKyAgICAgICAgcmVzdWx0ID0gbHRjMjk5MF92\n"
- "b2x0YWdlX3RvX2ludCh2YWwpICogMTk0MiAvICg0ICogMTAwKTsKPj4gKyAgICB9IGVsc2UgeyAv\n"
- "KiBWY2MsIDMwNS4xOM68Vi9MU0IsIDIuNVYgb2Zmc2V0ICovCj4+ICsgICAgICAgIHJlc3VsdCA9\n"
- "IGx0YzI5OTBfdm9sdGFnZV90b19pbnQodmFsKSAqIDMwNTE4IC8gKDQgKiAxMDAgKiAxMDAwKTsK\n"
- "Pj4gKyAgICAgICAgcmVzdWx0ICs9IDI1MDA7Cj4+ICsgICAgfQo+PiArCj4gV2l0aCB0aGUgcmVn\n"
- "aXN0ZXIgaW4gaW5kZXggKHNlZSBiZWxvdykgdGhpcyBjb3VsZCBiZQo+Cj4gICAgICB2YWwgPSBp\n"
- "MmNfc21idXNfcmVhZF93b3JkX3N3YXBwZWQoaTJjLCBpbmRleCk7Cj4KPiAgICAgIHN3aXRjaCAo\n"
- "aW5kZXgpIHsKPiAgICAgIGNhc2UgTFRDMjk5MF9USU5UX01TQjoKPiAgICAgICAgICB2YWwgPSAo\n"
- "dmFsICYgMHgxRkZGKSA8PCAzOwo+ICAgICAgICAgIHJlc3VsdCA9ICh2YWwgKiAxMDAwKSA+PiA3\n"
- "Owo+ICAgICAgICAgIGJyZWFrOwo+ICAgICAgY2FzZSBMVEMyOTkwX1YxX01TQjoKPiAgICAgIGNh\n"
- "c2UgTFRDMjk5MF9WMl9NU0I6Cj4gICAgICAgICAgLi4uCj4gICAgICAgICAgcmVzdWx0ID0gbHRj\n"
- "Mjk5MF92b2x0YWdlX3RvX2ludCh2YWwpICogMTk0MiAvICg0ICogMTAwKTsKPiAgICAgICAgICBi\n"
- "cmVhazsKPiAgICAgIGNhc2UgTFRDMjk5MF9WQ0NfTVNCOgo+ICAgICAgICAgIHJlc3VsdCA9IGx0\n"
- "YzI5OTBfdm9sdGFnZV90b19pbnQodmFsKSAqIDMwNTE4IC8gKDQgKiAxMDAgKiAxMDAwKTsKPiAg\n"
- "ICAgICAgICByZXN1bHQgKz0gMjUwMDsKPiAgICAgICAgICBicmVhazsKPiAgICAgIGRlZmF1bHQ6\n"
- "Cj4gICAgICAgICAgcmVzdWx0ID0gMDsgICAgLyogd29uJ3QgaGFwcGVuLCBtYWtlcyBjb21waWxl\n"
- "ciBoYXBweSAqLwo+ICAgICAgICAgIGJyZWFrOwo+ICAgICAgfQo+Cj4gd2hpY2ggSSB0aGluayB3\n"
- "b3VsZCBiZSBlYXNpZXIgdG8gdW5kZXJzdGFuZC4KCkFncmVlLCBnb29kIHBvaW50LiBBbHNvIHVz\n"
- "aW5nIHRoZSByZWdpc3RlciBuYW1lcyBoZWxwcyByZWFkYWJpbGl0eS4KCj4+ICsgICAgcmV0dXJu\n"
- "IHJlc3VsdDsKPj4gK30KPj4gKwo+PiArc3RhdGljIHNzaXplX3QgbHRjMjk5MF9zaG93X3ZhbHVl\n"
- "KHN0cnVjdCBkZXZpY2UgKmRldiwKPj4gKyAgICAgICAgICAgICAgICAgIHN0cnVjdCBkZXZpY2Vf\n"
- "YXR0cmlidXRlICpkYSwgY2hhciAqYnVmKQo+PiArewo+PiArICAgIHN0cnVjdCBzZW5zb3JfZGV2\n"
- "aWNlX2F0dHJpYnV0ZSAqYXR0ciA9IHRvX3NlbnNvcl9kZXZfYXR0cihkYSk7Cj4+ICsgICAgaW50\n"
- "IHZhbHVlOwo+PiArCj4+ICsgICAgdmFsdWUgPSBsdGMyOTkwX2dldF92YWx1ZShkZXZfZ2V0X2Ry\n"
- "dmRhdGEoZGV2KSwgYXR0ci0+aW5kZXgpOwo+PiArICAgIHJldHVybiBzbnByaW50ZihidWYsIFBB\n"
- "R0VfU0laRSwgIiVkXG4iLCB2YWx1ZSk7Cj4+ICt9Cj4+ICsKPj4gK3N0YXRpYyBTRU5TT1JfREVW\n"
- "SUNFX0FUVFIodGVtcDFfaW5wdXQsIFNfSVJVR08sIGx0YzI5OTBfc2hvd192YWx1ZSwgTlVMTCwg\n"
- "MCk7Cj4+ICtzdGF0aWMgU0VOU09SX0RFVklDRV9BVFRSKGN1cnIxX2lucHV0LCBTX0lSVUdPLCBs\n"
- "dGMyOTkwX3Nob3dfdmFsdWUsIE5VTEwsIDEpOwo+PiArc3RhdGljIFNFTlNPUl9ERVZJQ0VfQVRU\n"
- "UihjdXJyMl9pbnB1dCwgU19JUlVHTywgbHRjMjk5MF9zaG93X3ZhbHVlLCBOVUxMLCAzKTsKPj4g\n"
- "K3N0YXRpYyBTRU5TT1JfREVWSUNFX0FUVFIoaW4wX2lucHV0LCBTX0lSVUdPLCBsdGMyOTkwX3No\n"
- "b3dfdmFsdWUsIE5VTEwsIDUpOwo+Cj4gQ29uc2lkZXIgcHJvdmlkaW5nIHRoZSByZWdpc3RlciBN\n"
- "U0IgaW4gaW5kZXguCj4KPiBFeGFtcGxlOgo+ICAgICAgc3RhdGljIFNFTlNPUl9ERVZJQ0VfQVRU\n"
- "Uih0ZW1wMV9pbnB1dCwgU19JUlVHTywgbHRjMjk5MF9zaG93X3ZhbHVlLCBOVUxMLAo+IExUQzI5\n"
- "OTBfVElOVF9NU0IpOwoKQWdyZWUsIGFzIGFib3ZlLgoKPj4gKwo+PiArc3RhdGljIHN0cnVjdCBh\n"
- "dHRyaWJ1dGUgKmx0YzI5OTBfYXR0cnNbXSA9IHsKPj4gKyAgICAmc2Vuc29yX2Rldl9hdHRyX3Rl\n"
- "bXAxX2lucHV0LmRldl9hdHRyLmF0dHIsCj4+ICsgICAgJnNlbnNvcl9kZXZfYXR0cl9jdXJyMV9p\n"
- "bnB1dC5kZXZfYXR0ci5hdHRyLAo+PiArICAgICZzZW5zb3JfZGV2X2F0dHJfY3VycjJfaW5wdXQu\n"
- "ZGV2X2F0dHIuYXR0ciwKPj4gKyAgICAmc2Vuc29yX2Rldl9hdHRyX2luMF9pbnB1dC5kZXZfYXR0\n"
- "ci5hdHRyLAo+PiArICAgIE5VTEwsCj4+ICt9Owo+PiArQVRUUklCVVRFX0dST1VQUyhsdGMyOTkw\n"
- "KTsKPj4gKwo+PiArc3RhdGljIGludCBsdGMyOTkwX2kyY19wcm9iZShzdHJ1Y3QgaTJjX2NsaWVu\n"
- "dCAqaTJjLAo+PiArICAgIGNvbnN0IHN0cnVjdCBpMmNfZGV2aWNlX2lkICppZCkKPgo+IFBsZWFz\n"
- "ZSBhbGlnbiBjb250aW51YXRpb24gbGluZXMgd2l0aCAnKCcuCj4KPj4gK3sKPj4gKyAgICBpbnQg\n"
- "cmV0Owo+PiArICAgIHN0cnVjdCBkZXZpY2UgKmh3bW9uX2RldjsKPj4gKwo+PiArICAgIGlmICgh\n"
- "aTJjX2NoZWNrX2Z1bmN0aW9uYWxpdHkoaTJjLT5hZGFwdGVyLCBJMkNfRlVOQ19TTUJVU19CWVRF\n"
- "X0RBVEEpKQo+Cj4gQWxzbyBuZWVkIGNhcGFiaWxpdHkgdG8gcmVhZCB3b3Jkcy4KCkd1ZXNzIHNv\n"
- "Li4uCgo+Cj4+ICsgICAgICAgIHJldHVybiAtRU5PREVWOwo+PiArCj4+ICsgICAgLyogU2V0dXAg\n"
- "Y29udGludW91cyBtb2RlLCBjdXJyZW50IG1vbml0b3IgKi8KPj4gKyAgICByZXQgPSBpMmNfc21i\n"
- "dXNfd3JpdGVfYnl0ZV9kYXRhKGkyYywgTFRDMjk5MF9DT05UUk9MLAo+PiArICAgICAgICBMVEMy\n"
- "OTkwX0NPTlRST0xfTUVBU1VSRV9BTEwgfCBMVEMyOTkwX0NPTlRST0xfTU9ERV9DVVJSRU5UKTsK\n"
- "Pj4gKyAgICBpZiAocmV0IDwgMCkgewo+PiArICAgICAgICBkZXZfZXJyKCZpMmMtPmRldiwgIkVy\n"
- "cm9yOiBGYWlsZWQgdG8gc2V0IGNvbnRyb2wgbW9kZS5cbiIpOwo+PiArICAgICAgICByZXR1cm4g\n"
- "cmV0Owo+PiArICAgIH0KPj4gKyAgICAvKiBUcmlnZ2VyIG9uY2UgdG8gc3RhcnQgY29udGludW91\n"
- "cyBjb252ZXJzaW9uICovCj4+ICsgICAgcmV0ID0gaTJjX3NtYnVzX3dyaXRlX2J5dGVfZGF0YShp\n"
- "MmMsIExUQzI5OTBfVFJJR0dFUiwgMSk7Cj4+ICsgICAgaWYgKHJldCA8IDApIHsKPj4gKyAgICAg\n"
- "ICAgZGV2X2VycigmaTJjLT5kZXYsICJFcnJvcjogRmFpbGVkIHRvIHN0YXJ0IGFxdWlzaXRpb24u\n"
- "XG4iKTsKPgo+IHMvYXF1aXNpdGlvbi9hY3F1aXNpdGlvbi8KPgo+PiArICAgICAgICByZXR1cm4g\n"
- "cmV0Owo+PiArICAgIH0KPj4gKwo+PiArICAgIGh3bW9uX2RldiA9IGRldm1faHdtb25fZGV2aWNl\n"
- "X3JlZ2lzdGVyX3dpdGhfZ3JvdXBzKCZpMmMtPmRldiwKPj4gKyAgICAgICAgICAgICAgICAgICAg\n"
- "ICAgICAgICAgICBpMmMtPm5hbWUsCj4+ICsgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAg\n"
- "aTJjLAo+PiArICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGx0YzI5OTBfZ3JvdXBzKTsK\n"
- "Pj4gKwo+PiArICAgIHJldHVybiBQVFJfRVJSX09SX1pFUk8oaHdtb25fZGV2KTsKPj4gK30KPj4g\n"
- "Kwo+PiArc3RhdGljIGNvbnN0IHN0cnVjdCBpMmNfZGV2aWNlX2lkIGx0YzI5OTBfaTJjX2lkW10g\n"
- "PSB7Cj4+ICsgICAgeyAibHRjMjk5MCIsIDAgfSwKPj4gKyAgICB7fQo+PiArfTsKPj4gK01PRFVM\n"
- "RV9ERVZJQ0VfVEFCTEUoaTJjLCBsdGMyOTkwX2kyY19pZCk7Cj4+ICsKPj4gK3N0YXRpYyBzdHJ1\n"
- "Y3QgaTJjX2RyaXZlciBsdGMyOTkwX2kyY19kcml2ZXIgPSB7Cj4+ICsgICAgLmRyaXZlciA9IHsK\n"
- "Pj4gKyAgICAgICAgLm5hbWUgPSAibHRjMjk5MCIsCj4+ICsgICAgfSwKPj4gKyAgICAucHJvYmUg\n"
- "ICAgPSBsdGMyOTkwX2kyY19wcm9iZSwKPj4gKyAgICAuaWRfdGFibGUgPSBsdGMyOTkwX2kyY19p\n"
- "ZCwKPj4gK307Cj4+ICsKPj4gK21vZHVsZV9pMmNfZHJpdmVyKGx0YzI5OTBfaTJjX2RyaXZlcik7\n"
- "Cj4+ICsKPj4gK01PRFVMRV9ERVNDUklQVElPTigiTFRDMjk5MCBTZW5zb3IgRHJpdmVyIik7Cj4+\n"
- "ICtNT0RVTEVfQVVUSE9SKCJUb3BpYyBFbWJlZGRlZCBQcm9kdWN0cyIpOwo+PiArTU9EVUxFX0xJ\n"
- "Q0VOU0UoIkdQTCB2MiIpOwo+Pgo+CgoKCktpbmQgcmVnYXJkcywKCk1pa2UgTG9vaWptYW5zClN5\n"
- "c3RlbSBFeHBlcnQKClRPUElDIEVtYmVkZGVkIFByb2R1Y3RzCkVpbmRob3ZlbnNld2VnIDMyLUMs\n"
- "IE5MLTU2ODMgS0ggQmVzdApQb3N0YnVzIDQ0MCwgTkwtNTY4MCBBSyBCZXN0ClRlbGVmb29uOiAr\n"
- "MzEgKDApIDQ5OSAzMyA2OSA3OQpFLW1haWw6IG1pa2UubG9vaWptYW5zQHRvcGljcHJvZHVjdHMu\n"
- "Y29tCldlYnNpdGU6IHd3dy50b3BpY3Byb2R1Y3RzLmNvbQoKUGxlYXNlIGNvbnNpZGVyIHRoZSBl\n"
- "bnZpcm9ubWVudCBiZWZvcmUgcHJpbnRpbmcgdGhpcyBlLW1haWwKCgoKCgoKX19fX19fX19fX19f\n"
- "X19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX18KbG0tc2Vuc29ycyBtYWlsaW5nIGxp\n"
- "c3QKbG0tc2Vuc29yc0BsbS1zZW5zb3JzLm9yZwpodHRwOi8vbGlzdHMubG0tc2Vuc29ycy5vcmcv\n"
- bWFpbG1hbi9saXN0aW5mby9sbS1zZW5zb3Jz
+ "\357\273\277On 13-01-16 14:24, Guenter Roeck wrote:\n"
+ "> On 01/13/2016 03:05 AM, Mike Looijmans wrote:\n"
+ ">> This adds support for the Linear Technology LTC2990  I2C System Monitor.\n"
+ ">> The LTC2990 supports a combination of voltage, current and temperature\n"
+ ">> monitoring. This driver currently only supports reading two currents\n"
+ ">> by measuring two differential voltages across series resistors, in\n"
+ ">> addition to the Vcc supply voltage and internal temperature.\n"
+ ">>\n"
+ ">> This is sufficient to support the Topic Miami SOM which uses this chip\n"
+ ">> to monitor the currents flowing into the FPGA and the CPU parts.\n"
+ ">>\n"
+ ">> Signed-off-by: Mike Looijmans <mike.looijmans@topic.nl>\n"
+ ">\n"
+ "> Mike,\n"
+ ">\n"
+ "> That looks much better. Can you send me the output of i2cdump for the chip ?\n"
+ "> That would help me writing module test code for it.\n"
+ "\n"
+ "I'm kinda interested into how that would work.\n"
+ "\n"
+ "I'll have to remove the driver first to get i2cdump to work on the chip. I \n"
+ "cannot force a device removal from user space while running, can I?\n"
+ "And i suppose you want a dump of a chip in running status? (On boot, all are \n"
+ "registers are simply set to zero)\n"
+ "\n"
+ "\n"
+ "> Thanks,\n"
+ "> Guenter\n"
+ ">\n"
+ ">> ---\n"
+ ">> v2: Processed all review comments.\n"
+ ">>      Put chip into continuous measurement mode.\n"
+ ">>      Added ducumentation.\n"
+ ">>      Use standard hwmon interfaces and macros.\n"
+ ">>\n"
+ ">>   Documentation/hwmon/ltc2990 |  44 ++++++++++++\n"
+ ">>   drivers/hwmon/Kconfig       |  14 ++++\n"
+ ">>   drivers/hwmon/Makefile      |   1 +\n"
+ ">>   drivers/hwmon/ltc2990.c     | 160\n"
+ ">> ++++++++++++++++++++++++++++++++++++++++++++\n"
+ ">>   4 files changed, 219 insertions(+)\n"
+ ">>   create mode 100644 Documentation/hwmon/ltc2990\n"
+ ">>   create mode 100644 drivers/hwmon/ltc2990.c\n"
+ ">>\n"
+ ">> diff --git a/Documentation/hwmon/ltc2990 b/Documentation/hwmon/ltc2990\n"
+ ">> new file mode 100644\n"
+ ">> index 0000000..838b74e\n"
+ ">> --- /dev/null\n"
+ ">> +++ b/Documentation/hwmon/ltc2990\n"
+ ">> @@ -0,0 +1,44 @@\n"
+ ">> +Kernel driver ltc2990\n"
+ ">> +=====================\n"
+ ">> +\n"
+ ">> +Supported chips:\n"
+ ">> +  * Linear Technology LTC2990\n"
+ ">> +    Prefix: 'ltc2990'\n"
+ ">> +    Addresses scanned: -\n"
+ ">> +    Datasheet: http://www.linear.com/product/ltc2990\n"
+ ">> +\n"
+ ">> +Author: Mike Looijmans <mike.looijmans@topic.nl>\n"
+ ">> +\n"
+ ">> +\n"
+ ">> +Description\n"
+ ">> +-----------\n"
+ ">> +\n"
+ ">> +LTC2990 is a Quad I2C Voltage, Current and Temperature Monitor.\n"
+ ">> +The chip's inputs can measure 4 voltages, or two inputs together (1+2 and 3+4)\n"
+ ">> +can be combined to measure a differential voltage, which is typically used to\n"
+ ">> +measure current through a series resistor, or a temperature.\n"
+ ">> +\n"
+ ">> +This driver currently uses the 2x differential mode only. In order to support\n"
+ ">> +other modes, the driver will need to be expanded.\n"
+ ">> +\n"
+ ">> +\n"
+ ">> +Usage Notes\n"
+ ">> +-----------\n"
+ ">> +\n"
+ ">> +This driver does not probe for PMBus devices. You will have to instantiate\n"
+ ">> +devices explicitly.\n"
+ ">> +\n"
+ ">> +\n"
+ ">> +Sysfs attributes\n"
+ ">> +----------------\n"
+ ">> +\n"
+ ">> +The \"curr*_input\" measurements actually report the voltage drop across the\n"
+ ">> +input pins in microvolts. This is equivalent to the current through a 1mOhm\n"
+ ">> +sense resistor. Divide the reported value by the actual sense resistor value\n"
+ ">> +in mOhm to get the actual value.\n"
+ ">> +\n"
+ ">> +in0_input     Voltage at Vcc pin in millivolt (range 2.5V to 5V)\n"
+ ">> +temp1_input   Internal chip temperature in millidegrees Celcius\n"
+ ">> +curr1_input   Current in mA across v1-v2 assuming a 1mOhm sense resistor.\n"
+ ">> +curr2_input   Current in mA across v3-v4 assuming a 1mOhm sense resistor.\n"
+ ">> +\n"
+ ">> diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig\n"
+ ">> index 80a73bf..8a31d64 100644\n"
+ ">> --- a/drivers/hwmon/Kconfig\n"
+ ">> +++ b/drivers/hwmon/Kconfig\n"
+ ">> @@ -685,6 +685,20 @@ config SENSORS_LTC2945\n"
+ ">>         This driver can also be built as a module. If so, the module will\n"
+ ">>         be called ltc2945.\n"
+ ">>\n"
+ ">> +config SENSORS_LTC2990\n"
+ ">> +    tristate \"Linear Technology LTC2990 (current monitoring mode only)\"\n"
+ ">> +    depends on I2C\n"
+ ">> +    help\n"
+ ">> +      If you say yes here you get support for Linear Technology LTC2990\n"
+ ">> +      I2C System Monitor. The LTC2990 supports a combination of voltage,\n"
+ ">> +      current and temperature monitoring, but in addition to the Vcc supply\n"
+ ">> +      voltage and chip temperature, this driver currently only supports\n"
+ ">> +      reading two currents by measuring two differential voltages across\n"
+ ">> +      series resistors.\n"
+ ">> +\n"
+ ">> +      This driver can also be built as a module. If so, the module will\n"
+ ">> +      be called ltc2990.\n"
+ ">> +\n"
+ ">>   config SENSORS_LTC4151\n"
+ ">>       tristate \"Linear Technology LTC4151\"\n"
+ ">>       depends on I2C\n"
+ ">> diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile\n"
+ ">> index 12a3239..e4bd15b 100644\n"
+ ">> --- a/drivers/hwmon/Makefile\n"
+ ">> +++ b/drivers/hwmon/Makefile\n"
+ ">> @@ -101,6 +101,7 @@ obj-$(CONFIG_SENSORS_LM95234)    += lm95234.o\n"
+ ">>   obj-$(CONFIG_SENSORS_LM95241)    += lm95241.o\n"
+ ">>   obj-$(CONFIG_SENSORS_LM95245)    += lm95245.o\n"
+ ">>   obj-$(CONFIG_SENSORS_LTC2945)    += ltc2945.o\n"
+ ">> +obj-$(CONFIG_SENSORS_LTC2990)    += ltc2990.o\n"
+ ">>   obj-$(CONFIG_SENSORS_LTC4151)    += ltc4151.o\n"
+ ">>   obj-$(CONFIG_SENSORS_LTC4215)    += ltc4215.o\n"
+ ">>   obj-$(CONFIG_SENSORS_LTC4222)    += ltc4222.o\n"
+ ">> diff --git a/drivers/hwmon/ltc2990.c b/drivers/hwmon/ltc2990.c\n"
+ ">> new file mode 100644\n"
+ ">> index 0000000..3720ff7\n"
+ ">> --- /dev/null\n"
+ ">> +++ b/drivers/hwmon/ltc2990.c\n"
+ ">> @@ -0,0 +1,160 @@\n"
+ ">> +/*\n"
+ ">> + * Driver for Linear Technology LTC2990 power monitor\n"
+ ">> + *\n"
+ ">> + * Copyright (C) 2014 Topic Embedded Products\n"
+ ">> + * Author: Mike Looijmans <mike.looijmans@topic.nl>\n"
+ ">> + *\n"
+ ">> + * License: GPLv2\n"
+ ">> + *\n"
+ ">> + * This driver assumes the chip is wired as a dual current monitor, and\n"
+ ">> + * reports the voltage drop across two series resistors. It also reports\n"
+ ">> + * the chip's internal temperature and Vcc power supply voltage.\n"
+ ">> + */\n"
+ ">> +\n"
+ ">> +#include <linux/delay.h>\n"
+ "\n"
+ "Not needed, will be removed in v3\n"
+ "\n"
+ ">> +#include <linux/err.h>\n"
+ ">> +#include <linux/hwmon.h>\n"
+ ">> +#include <linux/hwmon-sysfs.h>\n"
+ ">> +#include <linux/i2c.h>\n"
+ ">> +#include <linux/kernel.h>\n"
+ ">> +#include <linux/module.h>\n"
+ ">> +#include <linux/slab.h>\n"
+ "\n"
+ "Not needed\n"
+ "\n"
+ ">> +\n"
+ ">> +#define LTC2990_STATUS    0x00\n"
+ ">> +#define LTC2990_CONTROL    0x01\n"
+ ">> +#define LTC2990_TRIGGER    0x02\n"
+ ">> +#define LTC2990_TINT_MSB    0x04\n"
+ ">> +#define LTC2990_TINT_LSB    0x05\n"
+ ">> +#define LTC2990_V1_MSB    0x06\n"
+ ">> +#define LTC2990_V1_LSB    0x07\n"
+ ">> +#define LTC2990_V2_MSB    0x08\n"
+ ">> +#define LTC2990_V2_LSB    0x09\n"
+ ">> +#define LTC2990_V3_MSB    0x0A\n"
+ ">> +#define LTC2990_V3_LSB    0x0B\n"
+ ">> +#define LTC2990_V4_MSB    0x0C\n"
+ ">> +#define LTC2990_V4_LSB    0x0D\n"
+ ">> +#define LTC2990_VCC_MSB    0x0E\n"
+ ">> +#define LTC2990_VCC_LSB    0x0F\n"
+ ">> +\n"
+ ">\n"
+ "> LSB not used.\n"
+ "\n"
+ "Agree. Will remove them, it's clutter.\n"
+ "\n"
+ ">\n"
+ ">> +#define LTC2990_STATUS_BUSY    BIT(0)\n"
+ ">> +#define LTC2990_STATUS_TINT    BIT(1)\n"
+ ">> +#define LTC2990_STATUS_V1    BIT(2)\n"
+ ">> +#define LTC2990_STATUS_V2    BIT(3)\n"
+ ">> +#define LTC2990_STATUS_V3    BIT(4)\n"
+ ">> +#define LTC2990_STATUS_V4    BIT(5)\n"
+ ">> +#define LTC2990_STATUS_VCC    BIT(6)\n"
+ ">> +\n"
+ "> No longer used ?\n"
+ "\n"
+ "No need for status read when in continuous mode, so they have no point being here.\n"
+ "\n"
+ ">\n"
+ ">> +/* Only define control settings we actually use */\n"
+ ">\n"
+ "> Hmmm ... but not all are used.\n"
+ "\n"
+ "I think it's better to remove that comment :)\n"
+ "\n"
+ ">> +#define LTC2990_CONTROL_KELVIN        BIT(7)\n"
+ ">> +#define LTC2990_CONTROL_SINGLE        BIT(6)\n"
+ ">> +#define LTC2990_CONTROL_MEASURE_ALL    (0x3 << 3)\n"
+ ">> +#define LTC2990_CONTROL_MODE_CURRENT    0x06\n"
+ ">> +#define LTC2990_CONTROL_MODE_VOLTAGE    0x07\n"
+ ">> +\n"
+ ">> +/* convert raw register value to sign-extended integer in 16-bit range */\n"
+ ">> +static int ltc2990_voltage_to_int(int raw)\n"
+ ">> +{\n"
+ ">> +    if (raw & BIT(14)) {\n"
+ ">> +        return -(0x4000 - (raw & 0x3FFF)) << 2;\n"
+ ">> +    } else {\n"
+ ">> +        return (raw & 0x3FFF) << 2;\n"
+ ">> +    }\n"
+ ">> +}\n"
+ ">> +\n"
+ ">> +/* Return the converted value from the given register in uV or mC */\n"
+ ">> +static int ltc2990_get_value(struct i2c_client *i2c, u8 index)\n"
+ ">> +{\n"
+ ">> +    int val;\n"
+ ">> +    int result;\n"
+ ">> +\n"
+ ">> +    val = i2c_smbus_read_word_swapped(i2c, (index << 1) + LTC2990_TINT_MSB);\n"
+ ">> +    if (unlikely(val < 0))\n"
+ ">> +        return val;\n"
+ ">> +\n"
+ ">> +    if (index == 0) { /* internal temp, 0.0625 degrees/LSB, 13-bit  */\n"
+ ">> +        val = (val & 0x1FFF) << 3;\n"
+ ">> +        result = (val * 1000) >> 7;\n"
+ ">> +    } else if (index < 5) { /* Vx-Vy, 19.42uV/LSB */\n"
+ ">> +        result = ltc2990_voltage_to_int(val) * 1942 / (4 * 100);\n"
+ ">> +    } else { /* Vcc, 305.18\316\274V/LSB, 2.5V offset */\n"
+ ">> +        result = ltc2990_voltage_to_int(val) * 30518 / (4 * 100 * 1000);\n"
+ ">> +        result += 2500;\n"
+ ">> +    }\n"
+ ">> +\n"
+ "> With the register in index (see below) this could be\n"
+ ">\n"
+ ">      val = i2c_smbus_read_word_swapped(i2c, index);\n"
+ ">\n"
+ ">      switch (index) {\n"
+ ">      case LTC2990_TINT_MSB:\n"
+ ">          val = (val & 0x1FFF) << 3;\n"
+ ">          result = (val * 1000) >> 7;\n"
+ ">          break;\n"
+ ">      case LTC2990_V1_MSB:\n"
+ ">      case LTC2990_V2_MSB:\n"
+ ">          ...\n"
+ ">          result = ltc2990_voltage_to_int(val) * 1942 / (4 * 100);\n"
+ ">          break;\n"
+ ">      case LTC2990_VCC_MSB:\n"
+ ">          result = ltc2990_voltage_to_int(val) * 30518 / (4 * 100 * 1000);\n"
+ ">          result += 2500;\n"
+ ">          break;\n"
+ ">      default:\n"
+ ">          result = 0;    /* won't happen, makes compiler happy */\n"
+ ">          break;\n"
+ ">      }\n"
+ ">\n"
+ "> which I think would be easier to understand.\n"
+ "\n"
+ "Agree, good point. Also using the register names helps readability.\n"
+ "\n"
+ ">> +    return result;\n"
+ ">> +}\n"
+ ">> +\n"
+ ">> +static ssize_t ltc2990_show_value(struct device *dev,\n"
+ ">> +                  struct device_attribute *da, char *buf)\n"
+ ">> +{\n"
+ ">> +    struct sensor_device_attribute *attr = to_sensor_dev_attr(da);\n"
+ ">> +    int value;\n"
+ ">> +\n"
+ ">> +    value = ltc2990_get_value(dev_get_drvdata(dev), attr->index);\n"
+ ">> +    return snprintf(buf, PAGE_SIZE, \"%d\\n\", value);\n"
+ ">> +}\n"
+ ">> +\n"
+ ">> +static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, ltc2990_show_value, NULL, 0);\n"
+ ">> +static SENSOR_DEVICE_ATTR(curr1_input, S_IRUGO, ltc2990_show_value, NULL, 1);\n"
+ ">> +static SENSOR_DEVICE_ATTR(curr2_input, S_IRUGO, ltc2990_show_value, NULL, 3);\n"
+ ">> +static SENSOR_DEVICE_ATTR(in0_input, S_IRUGO, ltc2990_show_value, NULL, 5);\n"
+ ">\n"
+ "> Consider providing the register MSB in index.\n"
+ ">\n"
+ "> Example:\n"
+ ">      static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, ltc2990_show_value, NULL,\n"
+ "> LTC2990_TINT_MSB);\n"
+ "\n"
+ "Agree, as above.\n"
+ "\n"
+ ">> +\n"
+ ">> +static struct attribute *ltc2990_attrs[] = {\n"
+ ">> +    &sensor_dev_attr_temp1_input.dev_attr.attr,\n"
+ ">> +    &sensor_dev_attr_curr1_input.dev_attr.attr,\n"
+ ">> +    &sensor_dev_attr_curr2_input.dev_attr.attr,\n"
+ ">> +    &sensor_dev_attr_in0_input.dev_attr.attr,\n"
+ ">> +    NULL,\n"
+ ">> +};\n"
+ ">> +ATTRIBUTE_GROUPS(ltc2990);\n"
+ ">> +\n"
+ ">> +static int ltc2990_i2c_probe(struct i2c_client *i2c,\n"
+ ">> +    const struct i2c_device_id *id)\n"
+ ">\n"
+ "> Please align continuation lines with '('.\n"
+ ">\n"
+ ">> +{\n"
+ ">> +    int ret;\n"
+ ">> +    struct device *hwmon_dev;\n"
+ ">> +\n"
+ ">> +    if (!i2c_check_functionality(i2c->adapter, I2C_FUNC_SMBUS_BYTE_DATA))\n"
+ ">\n"
+ "> Also need capability to read words.\n"
+ "\n"
+ "Guess so...\n"
+ "\n"
+ ">\n"
+ ">> +        return -ENODEV;\n"
+ ">> +\n"
+ ">> +    /* Setup continuous mode, current monitor */\n"
+ ">> +    ret = i2c_smbus_write_byte_data(i2c, LTC2990_CONTROL,\n"
+ ">> +        LTC2990_CONTROL_MEASURE_ALL | LTC2990_CONTROL_MODE_CURRENT);\n"
+ ">> +    if (ret < 0) {\n"
+ ">> +        dev_err(&i2c->dev, \"Error: Failed to set control mode.\\n\");\n"
+ ">> +        return ret;\n"
+ ">> +    }\n"
+ ">> +    /* Trigger once to start continuous conversion */\n"
+ ">> +    ret = i2c_smbus_write_byte_data(i2c, LTC2990_TRIGGER, 1);\n"
+ ">> +    if (ret < 0) {\n"
+ ">> +        dev_err(&i2c->dev, \"Error: Failed to start aquisition.\\n\");\n"
+ ">\n"
+ "> s/aquisition/acquisition/\n"
+ ">\n"
+ ">> +        return ret;\n"
+ ">> +    }\n"
+ ">> +\n"
+ ">> +    hwmon_dev = devm_hwmon_device_register_with_groups(&i2c->dev,\n"
+ ">> +                               i2c->name,\n"
+ ">> +                               i2c,\n"
+ ">> +                               ltc2990_groups);\n"
+ ">> +\n"
+ ">> +    return PTR_ERR_OR_ZERO(hwmon_dev);\n"
+ ">> +}\n"
+ ">> +\n"
+ ">> +static const struct i2c_device_id ltc2990_i2c_id[] = {\n"
+ ">> +    { \"ltc2990\", 0 },\n"
+ ">> +    {}\n"
+ ">> +};\n"
+ ">> +MODULE_DEVICE_TABLE(i2c, ltc2990_i2c_id);\n"
+ ">> +\n"
+ ">> +static struct i2c_driver ltc2990_i2c_driver = {\n"
+ ">> +    .driver = {\n"
+ ">> +        .name = \"ltc2990\",\n"
+ ">> +    },\n"
+ ">> +    .probe    = ltc2990_i2c_probe,\n"
+ ">> +    .id_table = ltc2990_i2c_id,\n"
+ ">> +};\n"
+ ">> +\n"
+ ">> +module_i2c_driver(ltc2990_i2c_driver);\n"
+ ">> +\n"
+ ">> +MODULE_DESCRIPTION(\"LTC2990 Sensor Driver\");\n"
+ ">> +MODULE_AUTHOR(\"Topic Embedded Products\");\n"
+ ">> +MODULE_LICENSE(\"GPL v2\");\n"
+ ">>\n"
+ ">\n"
+ "\n"
+ "\n"
+ "\n"
+ "Kind regards,\n"
+ "\n"
+ "Mike Looijmans\n"
+ "System Expert\n"
+ "\n"
+ "TOPIC Embedded Products\n"
+ "Eindhovenseweg 32-C, NL-5683 KH Best\n"
+ "Postbus 440, NL-5680 AK Best\n"
+ "Telefoon: +31 (0) 499 33 69 79\n"
+ "E-mail: mike.looijmans@topicproducts.com\n"
+ "Website: www.topicproducts.com\n"
+ "\n"
+ Please consider the environment before printing this e-mail
 
-bf02236fb649ce32a2a5e2be850c124a17cf6bc1f195000846841abd549775be
+0e7bf1ef12197d70315070b79ee41219019dc8cfd28ba1041b2c813c5c18996b

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.