Gentoo Archives: gentoo-ppc-user

From: "Konstantin V. Gavrilenko" <mlists@××××××.com>
To: gentoo-ppc-user@l.g.o
Subject: Re: [gentoo-ppc-user] pbbuttonsd question
Date: Tue, 30 May 2006 22:33:55
Message-Id: 447CC7CB.7050705@arhont.com
In Reply to: Re: [gentoo-ppc-user] pbbuttonsd question by "Konstantin V. Gavrilenko"
1 Here is an answer from Ben, I still have to test it myself.
2
3
4
5 Benjamin Herrenschmidt wrote:
6 > On Tue, 2006-05-30 at 21:09 +0100, Konstantin V. Gavrilenko wrote:
7 > SNIP <
8
9
10 > Does this help ?
11 >
12 > Ben.
13 >
14 > ------
15 > From: Linux Kernel Mailing List <linux-kernel@×××××××××××.org>
16 > To: git-commits-head@×××××××××××.org
17 > Subject: [PATCH] powermac: Fix i2c on keywest based chips
18 > Date: Sun, 23 Apr 2006 17:11:14 GMT
19 >
20 > commit 60162e498e220d1f03bbee5bac0a9ddd6de60ae7
21 > tree 8cbcbea6060eb2b9f7d39784385efdfc6e947b52
22 > parent 28897731318dc8f63f683eed9091e446916ad706
23 > author Benjamin Herrenschmidt <benh@×××××××××××××××.org> Tue, 18 Apr
24 2006 14:11:53 +1000
25 > committer Paul Mackerras <paulus@×××××.org> Fri, 21 Apr 2006 22:29:46
26 +1000
27 >
28 > [PATCH] powermac: Fix i2c on keywest based chips
29 >
30 > The new i2c implementation for PowerMac has a regression that causes the
31 > hardware to go out of state when probing non-existent devices. While
32 > fixing that, I also found & fixed a couple of other corner cases. This
33 > fixes booting with a pbbuttons version that scans the i2c bus for an LMU
34 > controller among others. Tested on a dual G5 with thermal control (which
35 > has heavy i2c activity) with no problem so far.
36 >
37 > Signed-off-by: Benjamin Herrenschmidt <benh@×××××××××××××××.org>
38 > Signed-off-by: Paul Mackerras <paulus@×××××.org>
39 >
40 > arch/powerpc/platforms/powermac/low_i2c.c | 78
41 +++++++++++++-----------------
42 > 1 files changed, 35 insertions(+), 43 deletions(-)
43 >
44 > diff --git a/arch/powerpc/platforms/powermac/low_i2c.c
45 b/arch/powerpc/platforms/powermac/low_i2c.c
46 > index e14f9ac..df2343e 100644
47 > --- a/arch/powerpc/platforms/powermac/low_i2c.c
48 > +++ b/arch/powerpc/platforms/powermac/low_i2c.c
49 > @@ -231,6 +231,14 @@ static u8 kw_i2c_wait_interrupt(struct p
50 > return isr;
51 > }
52 >
53 > +static void kw_i2c_do_stop(struct pmac_i2c_host_kw *host, int result)
54 > +{
55 > + kw_write_reg(reg_control, KW_I2C_CTL_STOP);
56 > + host->state = state_stop;
57 > + host->result = result;
58 > +}
59 > +
60 > +
61 > static void kw_i2c_handle_interrupt(struct pmac_i2c_host_kw *host, u8
62 isr)
63 > {
64 > u8 ack;
65 > @@ -246,42 +254,36 @@ static void kw_i2c_handle_interrupt(stru
66 > }
67 >
68 > if (isr == 0) {
69 > + printk(KERN_WARNING "low_i2c: Timeout in i2c transfer"
70 > + " on keywest !\n");
71 > if (host->state != state_stop) {
72 > - DBG_LOW("KW: Timeout !\n");
73 > - host->result = -EIO;
74 > - goto stop;
75 > - }
76 > - if (host->state == state_stop) {
77 > - ack = kw_read_reg(reg_status);
78 > - if (ack & KW_I2C_STAT_BUSY)
79 > - kw_write_reg(reg_status, 0);
80 > - host->state = state_idle;
81 > - kw_write_reg(reg_ier, 0x00);
82 > - if (!host->polled)
83 > - complete(&host->complete);
84 > + kw_i2c_do_stop(host, -EIO);
85 > + return;
86 > }
87 > + ack = kw_read_reg(reg_status);
88 > + if (ack & KW_I2C_STAT_BUSY)
89 > + kw_write_reg(reg_status, 0);
90 > + host->state = state_idle;
91 > + kw_write_reg(reg_ier, 0x00);
92 > + if (!host->polled)
93 > + complete(&host->complete);
94 > return;
95 > }
96 >
97 > if (isr & KW_I2C_IRQ_ADDR) {
98 > ack = kw_read_reg(reg_status);
99 > if (host->state != state_addr) {
100 > - kw_write_reg(reg_isr, KW_I2C_IRQ_ADDR);
101 > WRONG_STATE("KW_I2C_IRQ_ADDR");
102 > - host->result = -EIO;
103 > - goto stop;
104 > + kw_i2c_do_stop(host, -EIO);
105 > }
106 > if ((ack & KW_I2C_STAT_LAST_AAK) == 0) {
107 > - host->result = -ENODEV;
108 > - DBG_LOW("KW: NAK on address\n");
109 > + host->result = -ENXIO;
110 > host->state = state_stop;
111 > - return;
112 > + DBG_LOW("KW: NAK on address\n");
113 > } else {
114 > - if (host->len == 0) {
115 > - kw_write_reg(reg_isr, KW_I2C_IRQ_ADDR);
116 > - goto stop;
117 > - }
118 > - if (host->rw) {
119 > + if (host->len == 0)
120 > + kw_i2c_do_stop(host, 0);
121 > + else if (host->rw) {
122 > host->state = state_read;
123 > if (host->len > 1)
124 > kw_write_reg(reg_control,
125 > @@ -308,25 +310,19 @@ static void kw_i2c_handle_interrupt(stru
126 > ack = kw_read_reg(reg_status);
127 > if ((ack & KW_I2C_STAT_LAST_AAK) == 0) {
128 > DBG_LOW("KW: nack on data write\n");
129 > - host->result = -EIO;
130 > - goto stop;
131 > + host->result = -EFBIG;
132 > + host->state = state_stop;
133 > } else if (host->len) {
134 > kw_write_reg(reg_data, *(host->data++));
135 > host->len--;
136 > - } else {
137 > - kw_write_reg(reg_control, KW_I2C_CTL_STOP);
138 > - host->state = state_stop;
139 > - host->result = 0;
140 > - }
141 > - kw_write_reg(reg_isr, KW_I2C_IRQ_DATA);
142 > + } else
143 > + kw_i2c_do_stop(host, 0);
144 > } else {
145 > - kw_write_reg(reg_isr, KW_I2C_IRQ_DATA);
146 > WRONG_STATE("KW_I2C_IRQ_DATA");
147 > - if (host->state != state_stop) {
148 > - host->result = -EIO;
149 > - goto stop;
150 > - }
151 > + if (host->state != state_stop)
152 > + kw_i2c_do_stop(host, -EIO);
153 > }
154 > + kw_write_reg(reg_isr, KW_I2C_IRQ_DATA);
155 > }
156 >
157 > if (isr & KW_I2C_IRQ_STOP) {
158 > @@ -340,14 +336,10 @@ static void kw_i2c_handle_interrupt(stru
159 > complete(&host->complete);
160 > }
161 >
162 > + /* Below should only happen in manual mode which we don't use ... */
163 > if (isr & KW_I2C_IRQ_START)
164 > kw_write_reg(reg_isr, KW_I2C_IRQ_START);
165 >
166 > - return;
167 > - stop:
168 > - kw_write_reg(reg_control, KW_I2C_CTL_STOP);
169 > - host->state = state_stop;
170 > - return;
171 > }
172 >
173 > /* Interrupt handler */
174 > @@ -544,11 +536,11 @@ static struct pmac_i2c_host_kw *__init k
175 > return NULL;
176 > }
177 >
178 > - /* Make sure IRA is disabled */
179 > + /* Make sure IRQ is disabled */
180 > kw_write_reg(reg_ier, 0);
181 >
182 > /* Request chip interrupt */
183 > - if (request_irq(host->irq, kw_i2c_irq, SA_SHIRQ, "keywest i2c", host))
184 > + if (request_irq(host->irq, kw_i2c_irq, 0, "keywest i2c", host))
185 > host->irq = NO_IRQ;
186 >
187 > printk(KERN_INFO "KeyWest i2c @0x%08x irq %d %s\n",
188 > -
189 > To unsubscribe from this list: send the line "unsubscribe
190 git-commits-head" in
191 > the body of a message to majordomo@×××××××××××.org
192 > More majordomo info at http://vger.kernel.org/majordomo-info.html
193 >
194
195
196
197
198 --
199 Respectfully,
200 Konstantin V. Gavrilenko
201
202 Managing Director
203 Arhont Ltd - Information Security
204
205 web: http://www.arhont.com
206 http://www.wi-foo.com
207 e-mail: k.gavrilenko@××××××.com
208
209 tel: +44 (0) 870 44 31337
210 fax: +44 (0) 117 969 0141
211
212 PGP: Key ID - 0xE81824F4
213 PGP: Server - keyserver.pgp.com
214 --
215 gentoo-ppc-user@g.o mailing list

Replies

Subject Author
Re: [gentoo-ppc-user] pbbuttonsd question Eric Robertson <ericrobe@×××××.com>