* Can't turn off bluetooth with discoverable mode on Lucid
From: Chao Deng @ 2010-03-23 9:41 UTC (permalink / raw)
To: linux-bluetooth
When I use "hciconfig" to turn off Bluetooth, I meet a problem that it
can't be turned off correctly when discoverable. I need to run
"hciconfig hci0 down" twice to turn off it, following is the log
information.
[LOG]
root@ubuntu-laptop:/home/ubuntu# hciconfig
hci0: Type: SDIO
BD Address: 00:24:23:10:97:A3 ACL MTU: 1021:7 SCO MTU: 240:3
UP RUNNING PSCAN ISCAN
RX bytes:2324 acl:0 sco:0 events:71 errors:0
TX bytes:2746 acl:0 sco:0 commands:71 errors:0
root@ubuntu-laptop:/home/ubuntu# hciconfig hci0 down
root@ubuntu-laptop:/home/ubuntu# hciconfig
hci0: Type: SDIO
BD Address: 00:24:23:10:97:A3 ACL MTU: 1021:7 SCO MTU: 240:3
UP RUNNING PSCAN
RX bytes:3467 acl:0 sco:0 events:105 errors:0
TX bytes:4227 acl:0 sco:0 commands:105 errors:0
root@ubuntu-laptop:/home/ubuntu# hciconfig hci0 down
root@ubuntu-laptop:/home/ubuntu# hciconfig
hci0: Type: SDIO
BD Address: 00:24:23:10:97:A3 ACL MTU: 1021:7 SCO MTU: 240:3
DOWN
RX bytes:3477 acl:0 sco:0 events:106 errors:0
TX bytes:4234 acl:0 sco:0 commands:106 errors:0
[/LOG]
At the first time of "hciconfig hci0 down", the bluetooth adapter is
turned off and then turned on again (who turn on it?). The mode is
changed from "UP RUNNING PSCAN ISCAN" to "DOWN" (I can't capture this
change), and then from "DOWN" to "UP RUNNING PSCAN" (This is what we
see after run this command). You can see the time stamp in the log
file (syslog)
At the second time, the bluetooth adapter is turned off, mode is
changed to "DOWN".
This is part of the /var/log/syslog, you can see the state of "HCI dev 0"
[LOG]
Jul 29 08:54:01 ubuntu-laptop bluetoothd[1061]: Bluetooth daemon 4.60
Jul 29 08:54:01 ubuntu-laptop bluetoothd[1062]: Starting SDP server
Jul 29 08:54:01 ubuntu-laptop bluetoothd[1062]: Starting experimental
netlink support
Jul 29 08:54:01 ubuntu-laptop bluetoothd[1062]: Failed to find
Bluetooth netlink family
Jul 29 08:54:01 ubuntu-laptop bluetoothd[1062]: Failed to init netlink plugin
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: Can't create GN bridge
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: Unable to start SCO
server socket
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: Failed to init audio plugin
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: HCI dev 0 registered
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: Failed to open RFKILL
control device
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: accept: Socket
operation on non-socket (88)
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: HCI dev 0 up
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: Starting security manager 0
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: Parsing
/etc/bluetooth/serial.conf failed: No such file or directory
Jul 29 08:54:02 ubuntu-laptop bluetoothd[1062]: Adapter
/org/bluez/1061/hci0 has been enabled
Jul 29 08:54:15 ubuntu-laptop AptDaemon: INFO: Initializing daemon
Jul 29 08:54:33 ubuntu-laptop bluetoothd[1062]: HCI dev 0 down
Jul 29 08:54:33 ubuntu-laptop bluetoothd[1062]: Adapter
/org/bluez/1061/hci0 has been disabled
Jul 29 08:54:33 ubuntu-laptop bluetoothd[1062]: Stopping security manager 0
Jul 29 08:54:33 ubuntu-laptop bluetoothd[1062]: HCI dev 0 up
Jul 29 08:54:33 ubuntu-laptop bluetoothd[1062]: Starting security manager 0
Jul 29 08:54:33 ubuntu-laptop bluetoothd[1062]: Adapter
/org/bluez/1061/hci0 has been enabled
Jul 29 08:59:16 ubuntu-laptop AptDaemon: INFO: Quiting due to inactivity
Jul 29 08:59:16 ubuntu-laptop AptDaemon: INFO: Shutdown was requested
Jul 29 09:06:29 ubuntu-laptop bluetoothd[1062]: HCI dev 0 down
Jul 29 09:06:29 ubuntu-laptop bluetoothd[1062]: Adapter
/org/bluez/1061/hci0 has been disabled
Jul 29 09:06:29 ubuntu-laptop bluetoothd[1062]: Stopping security manager 0
Jul 29 09:06:29 ubuntu-laptop bluetoothd[1062]: HCI dev 0 up
Jul 29 09:06:29 ubuntu-laptop bluetoothd[1062]: Starting security manager 0
Jul 29 09:06:29 ubuntu-laptop bluetoothd[1062]: Adapter
/org/bluez/1061/hci0 has been enabled
Jul 29 09:06:41 ubuntu-laptop bluetoothd[1062]: HCI dev 0 down
Jul 29 09:06:41 ubuntu-laptop bluetoothd[1062]: Adapter
/org/bluez/1061/hci0 has been disabled
Jul 29 09:06:41 ubuntu-laptop bluetoothd[1062]: Stopping security manager 0
[/LOG]
The release of Ubuntu that I use is Ubuntu Lucid.
root@ubuntu-laptop:/home/ubuntu# lsb_release -rd
Description: Ubuntu lucid (development branch)
Release: 10.04
And the bluez version is 4.60-0ubuntu5.
The kernel version is 2.6.32.9.
The test platform that I use is Dove (ARM platform), and the Bluetooth
Adapter is Marvell SD8688.
By the way, I have test it on Karmic with the same kernel and driver,
it's workable. I also try to downgrade the Bluez version from 4.60 to
4.51(used in Karmic release), but it doesn't help, the problem still
exists.
Then, I kill the process "bluetoothd" and try it again, I can run
"hciconfig hci0 down" only once to turn off it (from "UP RUNNING PSCAN
ISCAN" to "DOWN"). So maybe something happens and lets "bluetoothd" to
turn on the adapter, how to trace it?
Do anyone else have the same problem like me? Or could you share some
methods to debug it?
^ permalink raw reply
* Re: [PATCH] Fix display of last device classes in hciconfig
From: Vinicius Gomes @ 2010-03-22 21:36 UTC (permalink / raw)
To: Daniel Abraham; +Cc: linux-bluetooth
In-Reply-To: <2c3916b71003160533s714e9ef3h6c803f88a79f27d2@mail.gmail.com>
SGkgRGFuaWVsLAoKT24gVHVlLCBNYXIgMTYsIDIwMTAgYXQgOTozMyBBTSwgRGFuaWVsIEFicmFo
YW0KPGRhbmllbC5zaHJ1Z2dlZEBnbWFpbC5jb20+IHdyb3RlOgo+IFRoaXMgaXMgbXkgZmlyc3Qg
ZXZlciBwYXRjaCwgc28gaXQncyB2ZXJ5IHNpbXBsZS4uLgo+IEJhc2VkIG9uIGN1cnJlbnQgY29u
dGVudCBpbjoKPiBodHRwOi8vd3d3LmJsdWV0b290aC5vcmcvYXNzaWduZWQtbnVtYmVycy9iYXNl
YmFuZC5odG0KPgoKSXQncyBuaWNlIHRoYXQgdGhpcyBpcyB5b3VyIGZpcnN0IChvZiBtYW55LCBJ
IGhvcGUgOy0pIGNvbnRyaWJ1dGlvbiwKYnV0IEkgZmVlbCBpdCdzIGJldHRlciBpZiB3ZSBsZWZ0
IHRoZSBjb21taXQgbWVzc2FnZSB3aXRoIGp1c3QKZXhwbGFpbmluZyB3aGF0IHRoZSBwYXRjaCBk
b2VzLgoKPiBTaWduZWQtb2ZmLWJ5OiBEYW5pZWwgQWJyYWhhbSA8ZGFuaWVsLnNocnVnZ2VkQGdt
YWlsLmNvbT4KCldlIGRvbid0IHVzZSB0aGUgIlNpZ25lZC1vZmYtYnkiIGxpbmUgaW4gQmx1ZVog
dXNlcmxhbmQgY29kZS4KCj4gLS0tCj4gwqB0b29scy9oY2ljb25maWcuYyB8IMKgIDMwICsrKysr
KysrKysrKysrKysrKysrKysrKysrLS0tLQo+IMKgMSBmaWxlcyBjaGFuZ2VkLCAyNiBpbnNlcnRp
b25zKCspLCA0IGRlbGV0aW9ucygtKQo+Cj4gZGlmZiAtLWdpdCBhL3Rvb2xzL2hjaWNvbmZpZy5j
IGIvdG9vbHMvaGNpY29uZmlnLmMKPiBpbmRleCAzZjY4N2UwLi5jOTdjZTQ0IDEwMDY0NAo+IC0t
LSBhL3Rvb2xzL2hjaWNvbmZpZy5jCj4gKysrIGIvdG9vbHMvaGNpY29uZmlnLmMKPiBAQCAtNjQ1
LDggKzY0NSwyNiBAQCBzdGF0aWMgY2hhciAqZ2V0X21pbm9yX2RldmljZV9uYW1lKGludCBtYWpv
ciwgaW50IG1pbm9yKQo+IMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgcmV0dXJu
ICJHYW1lIjsKPiDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoH0KPiDCoCDCoCDCoCDCoCDCoCDCoCDC
oCDCoGJyZWFrOwo+IC0gwqAgwqAgwqAgY2FzZSA2MzogwqAgwqAgwqAgwqAvKiB1bmNhdGVnb3Jp
c2VkICovCj4gLSDCoCDCoCDCoCDCoCDCoCDCoCDCoCByZXR1cm4gIiI7CgpJIHRoaW5rIHRoYXQg
dGhlIHRlc3QgZm9yIHRoZSAiVW5jYXRlZ29yaXNlZCIgKHdoaWNoIHNlZW1zIHRvIGJlCm1pc3Nw
ZWxsZWQgaW4gbWFueSBwbGFjZXMpIGRldmljZSBjbGFzcyB3b3VsZCBiZSBiZXR0ZXIgc3RheWlu
ZyBoZXJlLApiZWNhdXNlIHRoZSBzYW1lIGNvZGUgaXMgdXNlZCBpbnNpZGUgaGNpdG9vbC5jLiBG
aXhpbmcgdGhlcmUgd291bGQgYmUKbmljZSB0b28uCgpBbm90aGVyIHRoaW5nLCBsb29rcyBsaWtl
IHRoaXMgImNhc2UgNjM6IiBpcyB3cm9uZywgIG1ham9yIGRldmljZQpjbGFzcyBpcyBhIDUgYml0
IG51bWJlciwgYW5kIHRoZSB1bmNhdGVnb3JpemVkIGRldmljZSBjbGFzcyBpcyBkZWZpbmVkCmFz
IDMxLiBMb29rcyBsaWtlIGEgbGVnYWN5IGZyb20gYW5jaWVudCB0aW1lcyA7LSkKCj4gKyDCoCDC
oCDCoCBjYXNlIDk6IC8qIGhlYWx0aCAqLwo+ICsgwqAgwqAgwqAgwqAgwqAgwqAgwqAgc3dpdGNo
KG1pbm9yKSB7Cj4gKyDCoCDCoCDCoCDCoCDCoCDCoCDCoCBjYXNlIDA6Cj4gKyDCoCDCoCDCoCDC
oCDCoCDCoCDCoCDCoCDCoCDCoCDCoCByZXR1cm4gIlVuZGVmaW5lZCI7Cj4gKyDCoCDCoCDCoCDC
oCDCoCDCoCDCoCBjYXNlIDE6Cj4gKyDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCBy
ZXR1cm4gIkJsb29kIFByZXNzdXJlIE1vbml0b3IiOwo+ICsgwqAgwqAgwqAgwqAgwqAgwqAgwqAg
Y2FzZSAyOgo+ICsgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgcmV0dXJuICJUaGVy
bW9tZXRlciI7Cj4gKyDCoCDCoCDCoCDCoCDCoCDCoCDCoCBjYXNlIDM6Cj4gKyDCoCDCoCDCoCDC
oCDCoCDCoCDCoCDCoCDCoCDCoCDCoCByZXR1cm4gIldlaWdoaW5nIFNjYWxlIjsKPiArIMKgIMKg
IMKgIMKgIMKgIMKgIMKgIGNhc2UgNDoKPiArIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKg
IMKgIHJldHVybiAiR2x1Y29zZSBNZXRlciI7Cj4gKyDCoCDCoCDCoCDCoCDCoCDCoCDCoCBjYXNl
IDU6Cj4gKyDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCByZXR1cm4gIlB1bHNlIE94
aW1ldGVyIjsKPiArIMKgIMKgIMKgIMKgIMKgIMKgIMKgIGNhc2UgNjoKPiArIMKgIMKgIMKgIMKg
IMKgIMKgIMKgIMKgIMKgIMKgIMKgIHJldHVybiAiSGVhcnQvUHVsc2UgUmF0ZSBNb25pdG9yIjsK
PiArIMKgIMKgIMKgIMKgIMKgIMKgIMKgIGNhc2UgNzoKPiArIMKgIMKgIMKgIMKgIMKgIMKgIMKg
IMKgIMKgIMKgIMKgIHJldHVybiAiSGVhbHRoIERhdGEgRGlzcGxheSI7Cj4gKyDCoCDCoCDCoCDC
oCDCoCDCoCDCoCB9Cj4gKyDCoCDCoCDCoCDCoCDCoCDCoCDCoCBicmVhazsKPiDCoCDCoCDCoCDC
oH0KPiDCoCDCoCDCoCDCoHJldHVybiAiVW5rbm93biAocmVzZXJ2ZWQpIG1pbm9yIGRldmljZSBj
bGFzcyI7Cj4gwqB9Cj4gQEAgLTY2OCw3ICs2ODYsOSBAQCBzdGF0aWMgdm9pZCBjbWRfY2xhc3Mo
aW50IGN0bCwgaW50IGhkZXYsIGNoYXIgKm9wdCkKPiDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDC
oCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCJBdWRpby9WaWRlbyIsCj4gwqAgwqAg
wqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAiUGVy
aXBoZXJhbCIsCj4gwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAgwqAg
wqAgwqAgwqAgwqAgwqAiSW1hZ2luZyIsCj4gLSDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDC
oCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCAiVW5jYXRlZ29yaXplZCIgfTsKPiArIMKgIMKg
IMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgICJXZWFy
YWJsZSIsCj4gKyDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoCDC
oCDCoCDCoCDCoCAiVG95IiwKPiArIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKg
IMKgIMKgIMKgIMKgIMKgIMKgIMKgICJIZWFsdGgiIH07Cj4gwqAgwqAgwqAgwqBpbnQgcyA9IGhj
aV9vcGVuX2RldihoZGV2KTsKPgo+IMKgIMKgIMKgIMKgaWYgKHMgPCAwKSB7Cj4gQEAgLTcwNiw3
ICs3MjYsOSBAQCBzdGF0aWMgdm9pZCBjbWRfY2xhc3MoaW50IGN0bCwgaW50IGhkZXYsIGNoYXIg
Km9wdCkKPiDCoCDCoCDCoCDCoCDCoCDCoCDCoCDCoH0gZWxzZQo+IMKgIMKgIMKgIMKgIMKgIMKg
IMKgIMKgIMKgIMKgIMKgIMKgcHJpbnRmKCJVbnNwZWNpZmllZCIpOwo+IMKgIMKgIMKgIMKgIMKg
IMKgIMKgIMKgcHJpbnRmKCJcblx0RGV2aWNlIENsYXNzOiAiKTsKPiAtIMKgIMKgIMKgIMKgIMKg
IMKgIMKgIGlmICgoY2xzWzFdICYgMHgxZikgPj0gc2l6ZW9mKG1ham9yX2RldmljZXMpIC8gc2l6
ZW9mKCptYWpvcl9kZXZpY2VzKSkKPiArIMKgIMKgIMKgIMKgIMKgIMKgIMKgIGlmICgweDFmID09
IGNsc1sxXSkKClRoaXMgdGVzdCBpcyBpbnZlcnRlZCwgaW4gQmx1ZVogY29kZSB3ZSB1c2UgdGhl
IGZvcm06ICh2YXJpYWJsZQpvcGVyYXRvciBjb25zdGFudCkKCj4gKyDCoCDCoCDCoCDCoCDCoCDC
oCDCoCDCoCDCoCDCoCDCoCBwcmludGYoIlVuY2F0ZWdvcml6ZWRcbiIpOwo+ICsgwqAgwqAgwqAg
wqAgwqAgwqAgwqAgZWxzZSBpZiAoKGNsc1sxXSAmIDB4MWYpID49IHNpemVvZihtYWpvcl9kZXZp
Y2VzKSAvIHNpemVvZigqbWFqb3JfZGV2aWNlcykpCgpTZWUgYWJvdmUuCgo+IMKgIMKgIMKgIMKg
IMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgcHJpbnRmKCJJbnZhbGlkIERldmljZSBDbGFzcyFcbiIp
Owo+IMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKgZWxzZQo+IMKgIMKgIMKgIMKgIMKgIMKgIMKgIMKg
IMKgIMKgIMKgIMKgcHJpbnRmKCIlcywgJXNcbiIsIG1ham9yX2RldmljZXNbY2xzWzFdICYgMHgx
Zl0sCj4gLS0KPiAxLjYuNi4xCj4gLS0KPiBUbyB1bnN1YnNjcmliZSBmcm9tIHRoaXMgbGlzdDog
c2VuZCB0aGUgbGluZSAidW5zdWJzY3JpYmUgbGludXgtYmx1ZXRvb3RoIiBpbgo+IHRoZSBib2R5
IG9mIGEgbWVzc2FnZSB0byBtYWpvcmRvbW9Admdlci5rZXJuZWwub3JnCj4gTW9yZSBtYWpvcmRv
bW8gaW5mbyBhdCDCoGh0dHA6Ly92Z2VyLmtlcm5lbC5vcmcvbWFqb3Jkb21vLWluZm8uaHRtbAo+
CgoKQ2hlZXJzLAotLSAKVmluaWNpdXMgR29tZXMKSU5kVCAtIEluc3RpdHV0byBOb2tpYSBkZSBU
ZWNub2xvZ2lhCg==
^ permalink raw reply
* Re: BlueZ GSoC 2010
From: Bastien Nocera @ 2010-03-22 17:27 UTC (permalink / raw)
To: Luiz Augusto von Dentz; +Cc: Vinicius Gomes, BlueZ
In-Reply-To: <2d5a2c101003220914m41188e22ha0872104d4c6db4f@mail.gmail.com>
On Mon, 2010-03-22 at 18:14 +0200, Luiz Augusto von Dentz wrote:
> Hi Bastien,
>
> On Mon, Mar 22, 2010 at 2:13 PM, Bastien Nocera <hadess@hadess.net> wrote:
> > Hey,
> >
> > On Thu, 2010-03-18 at 22:50 -0300, Vinicius Gomes wrote:
> >> Hi,
> >>
> >> BlueZ just got accepted as an organization for this year's Google
> >> Summer of Code.
> >>
> >> There is a small list of project ideas here[1], for the next days we
> >> need to polish it and add more content. Any help is appreciated.
> >>
> >> We are also looking for mentors, if this idea interests you, please
> >> contact me off-list or go to #bluez-gsoc at freenode, this is also
> >> where most of the discussion regarding GSoC will take place, in case
> >> you just want to follow it.
> >>
> >> As always, patches and suggestions are welcome ;-)
> >
> > A couple of comments:
> > - Is AVRCP 1.4 support really a full Summer's work? Could be with
> > PulseAudio or application integration?
>
> Some avrcp 1.4 needs some integration so I guess it is ok.
>
> > - The "any" adapter work is a waste of resources, as I've mentioned in
> > the past on the list.
>
> Well if it eliminates one round trip for most application I guess it
> is worth adding, and we might add other tricks as storage and API
> simplifications on top of it.
One round-trip at the cost of more code on your side. I'm really not
sure it's worth it.
> > - The VDP support probably needs kernel-level hacking as well, to avoid
> > being constrained to one of the supported frameworks, and create a
> > user-space driver for the device (using CUSE?)
>
> It could be considerate, but if that is a good idea to vdp it would
> also be for a2dp, there is also the problem that avdtp is currently
> implemented in bluetoothd so I wonder if we should start changing
> things or just implement vdp on top of the existing avdtp code.
Right, except that for sound we have a "broker" application in
PulseAudio. There's no such thing for V4L devices. In any case, it
should probably be a separate application that would take the data from
bluetoothd and make it available as a video device through v4l.
The VDP-using webcam I have uses MPEG-4 as the video codec, and you
probably don't want to have to reimplement that, so the broker app could
probably use GStreamer to make the video available.
> > I'd be happy to do testing and some integration work for both the VDP
> > and DUN works.
> >
> > I could also add:
> > - Port gnome-user-share to obexd, instead of obex-data-server (easy)
> > - Port osso-gwobex test suite and extend it (medium)
> > (Those 2 could be combined into one project)
> > - Printer (initial) setup integration in gnome-bluetooth (medium)
>
> I guess those are too gnome related for being in BlueZ, expect maybe
> gwobex, of course we could help/co/mentor projects under gnome
> organization.
Or vice-versa :)
Given that porting gnome-user-share to obexd shouldn't be a long winded
task, porting the osso-gwobex test suite would nicely complete it.
The printer integration work could probably be re-used by other
bluetoothd-setup front-ends like KDE.
> > - Extended hostname support (using xdg-hostname) (medium)
> > - Kernel driver and user-space changes for Sixaxis joypad (including
> > rumble). The bdaddr assignment would be done in the kernel, with a
> > helper in bluetoothd, extra functionality would be added in the kernel
> > for the other features (medium)
>
> Great ideas and those fits perfectly as bluez organization projects.
Cheers
^ permalink raw reply
* Re: BlueZ GSoC 2010
From: Luiz Augusto von Dentz @ 2010-03-22 16:14 UTC (permalink / raw)
To: Bastien Nocera; +Cc: Vinicius Gomes, BlueZ
In-Reply-To: <1269259999.21548.3330.camel@localhost.localdomain>
Hi Bastien,
On Mon, Mar 22, 2010 at 2:13 PM, Bastien Nocera <hadess@hadess.net> wrote:
> Hey,
>
> On Thu, 2010-03-18 at 22:50 -0300, Vinicius Gomes wrote:
>> Hi,
>>
>> BlueZ just got accepted as an organization for this year's Google
>> Summer of Code.
>>
>> There is a small list of project ideas here[1], for the next days we
>> need to polish it and add more content. Any help is appreciated.
>>
>> We are also looking for mentors, if this idea interests you, please
>> contact me off-list or go to #bluez-gsoc at freenode, this is also
>> where most of the discussion regarding GSoC will take place, in case
>> you just want to follow it.
>>
>> As always, patches and suggestions are welcome ;-)
>
> A couple of comments:
> - Is AVRCP 1.4 support really a full Summer's work? Could be with
> PulseAudio or application integration?
Some avrcp 1.4 needs some integration so I guess it is ok.
> - The "any" adapter work is a waste of resources, as I've mentioned in
> the past on the list.
Well if it eliminates one round trip for most application I guess it
is worth adding, and we might add other tricks as storage and API
simplifications on top of it.
> - The VDP support probably needs kernel-level hacking as well, to avoid
> being constrained to one of the supported frameworks, and create a
> user-space driver for the device (using CUSE?)
It could be considerate, but if that is a good idea to vdp it would
also be for a2dp, there is also the problem that avdtp is currently
implemented in bluetoothd so I wonder if we should start changing
things or just implement vdp on top of the existing avdtp code.
> I'd be happy to do testing and some integration work for both the VDP
> and DUN works.
>
> I could also add:
> - Port gnome-user-share to obexd, instead of obex-data-server (easy)
> - Port osso-gwobex test suite and extend it (medium)
> (Those 2 could be combined into one project)
> - Printer (initial) setup integration in gnome-bluetooth (medium)
I guess those are too gnome related for being in BlueZ, expect maybe
gwobex, of course we could help/co/mentor projects under gnome
organization.
> - Extended hostname support (using xdg-hostname) (medium)
> - Kernel driver and user-space changes for Sixaxis joypad (including
> rumble). The bdaddr assignment would be done in the kernel, with a
> helper in bluetoothd, extra functionality would be added in the kernel
> for the other features (medium)
Great ideas and those fits perfectly as bluez organization projects.
--
Luiz Augusto von Dentz
Computer Engineer
^ permalink raw reply
* Re: BlueZ GSoC 2010
From: Bastien Nocera @ 2010-03-22 12:13 UTC (permalink / raw)
To: Vinicius Gomes; +Cc: BlueZ
In-Reply-To: <2a9506371003181850h15a417a4u35bc0ed70e60f548@mail.gmail.com>
Hey,
On Thu, 2010-03-18 at 22:50 -0300, Vinicius Gomes wrote:
> Hi,
>
> BlueZ just got accepted as an organization for this year's Google
> Summer of Code.
>
> There is a small list of project ideas here[1], for the next days we
> need to polish it and add more content. Any help is appreciated.
>
> We are also looking for mentors, if this idea interests you, please
> contact me off-list or go to #bluez-gsoc at freenode, this is also
> where most of the discussion regarding GSoC will take place, in case
> you just want to follow it.
>
> As always, patches and suggestions are welcome ;-)
A couple of comments:
- Is AVRCP 1.4 support really a full Summer's work? Could be with
PulseAudio or application integration?
- The "any" adapter work is a waste of resources, as I've mentioned in
the past on the list.
- The VDP support probably needs kernel-level hacking as well, to avoid
being constrained to one of the supported frameworks, and create a
user-space driver for the device (using CUSE?)
I'd be happy to do testing and some integration work for both the VDP
and DUN works.
I could also add:
- Port gnome-user-share to obexd, instead of obex-data-server (easy)
- Port osso-gwobex test suite and extend it (medium)
(Those 2 could be combined into one project)
- Printer (initial) setup integration in gnome-bluetooth (medium)
- Extended hostname support (using xdg-hostname) (medium)
- Kernel driver and user-space changes for Sixaxis joypad (including
rumble). The bdaddr assignment would be done in the kernel, with a
helper in bluetoothd, extra functionality would be added in the kernel
for the other features (medium)
Cheers
^ permalink raw reply
* Re: [PATCH] Fix error not being propagated properly
From: Johan Hedberg @ 2010-03-22 11:11 UTC (permalink / raw)
To: Luiz Augusto von Dentz; +Cc: linux-bluetooth
In-Reply-To: <2d5a2c101003050536q61f16c12xb67a985234b3619@mail.gmail.com>
On Fri, Mar 05, 2010, Luiz Augusto von Dentz wrote:
> Now with the correct patch attached
>
> From 5dd57c233aa881faeaa6bfca147abcdb9e04dc93 Mon Sep 17 00:00:00 2001
> From: Luiz Augusto Von Dentz <luiz.dentz-von@nokia.com>
> Date: Fri, 5 Mar 2010 15:01:59 +0200
> Subject: [PATCH 11/11] Fix error not being propagated properly
>
> ---
> audio/headset.c | 4 ++--
> 1 files changed, 2 insertions(+), 2 deletions(-)
The first patch had some issues so I pushed my own fixed up version of
it. However, this second patch from you is now pushed (unchanged)
upstream.
Johan
^ permalink raw reply
* Re: [PATCH 2/2] Add sysfs speed attribute for wacom bluetooth tablet
From: Jiri Kosina @ 2010-03-22 8:48 UTC (permalink / raw)
To: Przemo Firszt
Cc: Bastien Nocera, linux-bluetooth, marcel, Peter Hutterer, Ping
In-Reply-To: <1268939541.3639.13.camel@pldmachine>
On Thu, 18 Mar 2010, Przemo Firszt wrote:
> > On Thu, 2010-03-18 at 15:26 +0000, Przemo Firszt wrote:
> >
> > > + unsigned char speed;
> >
> > Could you add some comments as to what values represent what speed?
> I changed name from 'speed' to 'high_speed' as per your comment below,
> so I think there is no need (unless you think otherwise).
> >
> > > +static ssize_t wacom_store_speed(struct device *dev,
> > > + struct device_attribute *attr,
> > > + const char *buf, size_t count)
> > > +{
> > > + struct hid_device *hdev = container_of(dev, struct hid_device,
> > > dev);
> > > + int new_speed;
> > > +
> > > + sscanf(buf, "%1d", &new_speed);
> >
> > You should check the retval of sscanf as well.
> Done, see attached patch.
> > > + if (new_speed == 0 || new_speed == 1) {
> > > + wacom_poke(hdev, new_speed);
> > > + return strnlen(buf, PAGE_SIZE);
> > > + } else
> > > + return -EINVAL;
> > > +}
> >
> > >
> > > +static DEVICE_ATTR(speed, S_IRUGO | S_IWUGO,
> > > + wacom_show_speed, wacom_store_speed);
> >
> > If there's only 2 speeds available, and it's actually a boolean, I'd
> > rather you used a name like "high_speed".
> >
> > Furthermore, wdata->speed doesn't look like it's initialised.
> It is initialised by the very first call of wacom_poke from wacom_probe
> function. Can you advise if it's enough?
> >
> > Did you test whether speed switching works after the device has been
> > started up?
> Yes, it works like a charm, both ways.
> [przemo@pldmachine ~]$ echo 0 > /sys/class/hidraw/hidraw1/device/speed
> and lag is gone,
> [przemo@pldmachine ~]$ echo 1 > /sys/class/hidraw/hidraw1/device/speed
> and "rubber band" effect is back.
The patch looks fine to me, so I have applied it to my tree.
Could you also please send a followup patch which would add
Documentation/ABI entry for the speed attribute?
Thanks,
--
Jiri Kosina
SUSE Labs, Novell Inc.
^ permalink raw reply
* Re: [PATCH 1/2] Add separate mode switching function wacom bluetooth pen tablet.
From: Jiri Kosina @ 2010-03-22 8:47 UTC (permalink / raw)
To: Bastien Nocera
Cc: Przemo Firszt, linux-bluetooth, marcel, Ping, Peter Hutterer
In-Reply-To: <1268926743.21548.1483.camel@localhost.localdomain>
On Thu, 18 Mar 2010, Bastien Nocera wrote:
> > Two patches to allow switching of reporting speed of wacom bluetooth
> > tablet from userspace through sysfs.
>
> Signed-off-by: Bastien Nocera <hadess@hadess.net>
Applied, thanks.
--
Jiri Kosina
SUSE Labs, Novell Inc.
^ permalink raw reply
* Re: [PATCH 2/4] Bluetooth: Change acknowledgement to use the value of txWindow
From: Gustavo F. Padovan @ 2010-03-22 3:33 UTC (permalink / raw)
To: Mike Tsai
Cc: linux-bluetooth@vger.kernel.org, marcel@holtmann.org,
mathewm@codeaurora.org
In-Reply-To: <35B17FE5076C7040809188FBE7913F983A1DA4F474@SC1EXMB-MBCL.global.atheros.com>
Hi Mike,
* Mike Tsai <Mike.Tsai@Atheros.com> [2010-03-17 14:47:49 -0700]:
> Just out of curiosity, where does this (pi->txWindow/6 + 1) come from?
L2CAP spec says that we don't need to ack every packet received, so I
have choose this number for optimization to not send an ack for each
packet received.
We can do a study and choose the better value for this, but it's better
to have the Extended Tx Window Implemented.
>
> Thanks,
>
> Mike
>
>
> -----Original Message-----
> From: linux-bluetooth-owner@vger.kernel.org [mailto:linux-bluetooth-owner@vger.kernel.org] On Behalf Of Gustavo F. Padovan
> Sent: Wednesday, March 17, 2010 11:54 AM
> To: linux-bluetooth@vger.kernel.org
> Cc: marcel@holtmann.org; gustavo@padovan.org; mathewm@codeaurora.org
> Subject: [PATCH 2/4] Bluetooth: Change acknowledgement to use the value of txWindow
>
> Now that we can set the txWindow we need to change the acknowledgement
> procedure to ack after each (pi->txWindow/6 + 1). The plus 1 is to avoid
> the zero value.
> It also renames pi->num_to_ack to a better name: pi->num_acked.
>
> Signed-off-by: Gustavo F. Padovan <gustavo@padovan.org>
> ---
> include/net/bluetooth/l2cap.h | 3 +--
> net/bluetooth/l2cap.c | 9 +++++----
> 2 files changed, 6 insertions(+), 6 deletions(-)
>
> diff --git a/include/net/bluetooth/l2cap.h b/include/net/bluetooth/l2cap.h
> index c7bf676..9358b9e 100644
> --- a/include/net/bluetooth/l2cap.h
> +++ b/include/net/bluetooth/l2cap.h
> @@ -30,7 +30,6 @@
> #define L2CAP_DEFAULT_MIN_MTU 48
> #define L2CAP_DEFAULT_FLUSH_TO 0xffff
> #define L2CAP_DEFAULT_TX_WINDOW 63
> -#define L2CAP_DEFAULT_NUM_TO_ACK (L2CAP_DEFAULT_TX_WINDOW/5)
> #define L2CAP_DEFAULT_MAX_TX 3
> #define L2CAP_DEFAULT_RETRANS_TO 1000 /* 1 second */
> #define L2CAP_DEFAULT_MONITOR_TO 12000 /* 12 seconds */
> @@ -333,7 +332,7 @@ struct l2cap_pinfo {
> __u8 frames_sent;
> __u8 unacked_frames;
> __u8 retry_count;
> - __u8 num_to_ack;
> + __u8 num_acked;
> __u16 sdu_len;
> __u16 partial_sdu_len;
> struct sk_buff *sdu;
> diff --git a/net/bluetooth/l2cap.c b/net/bluetooth/l2cap.c
> index 6679418..959be0f 100644
> --- a/net/bluetooth/l2cap.c
> +++ b/net/bluetooth/l2cap.c
> @@ -2248,7 +2248,7 @@ static inline void l2cap_ertm_init(struct sock *sk)
> l2cap_pi(sk)->expected_ack_seq = 0;
> l2cap_pi(sk)->unacked_frames = 0;
> l2cap_pi(sk)->buffer_seq = 0;
> - l2cap_pi(sk)->num_to_ack = 0;
> + l2cap_pi(sk)->num_acked = 0;
> l2cap_pi(sk)->frames_sent = 0;
>
> setup_timer(&l2cap_pi(sk)->retrans_timer,
> @@ -2571,7 +2571,7 @@ static int l2cap_parse_conf_rsp(struct sock *sk, void *rsp, int len, void *data,
> if (*result == L2CAP_CONF_SUCCESS) {
> switch (rfc.mode) {
> case L2CAP_MODE_ERTM:
> - pi->remote_tx_win = rfc.txwin_size;
> + pi->tx_win = rfc.txwin_size;
> pi->retrans_timeout = rfc.retrans_timeout;
> pi->monitor_timeout = rfc.monitor_timeout;
> pi->max_pdu_size = le16_to_cpu(rfc.max_pdu_size);
> @@ -3408,6 +3408,7 @@ static inline int l2cap_data_channel_iframe(struct sock *sk, u16 rx_control, str
> u8 tx_seq = __get_txseq(rx_control);
> u8 req_seq = __get_reqseq(rx_control);
> u8 sar = rx_control >> L2CAP_CTRL_SAR_SHIFT;
> + int num_to_ack = (pi->tx_win/6) + 1;
> int err = 0;
>
> BT_DBG("sk %p rx_control 0x%4.4x len %d", sk, rx_control, skb->len);
> @@ -3501,8 +3502,8 @@ expected:
>
> __mod_ack_timer();
>
> - pi->num_to_ack = (pi->num_to_ack + 1) % L2CAP_DEFAULT_NUM_TO_ACK;
> - if (pi->num_to_ack == L2CAP_DEFAULT_NUM_TO_ACK - 1)
> + pi->num_acked = (pi->num_acked + 1) % num_to_ack;
> + if (pi->num_acked == num_to_ack - 1)
> l2cap_send_ack(pi);
>
> return 0;
> --
> 1.6.4.4
>
> --
> To unsubscribe from this list: send the line "unsubscribe linux-bluetooth" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at http://vger.kernel.org/majordomo-info.html
--
Gustavo F. Padovan
http://padovan.org
^ permalink raw reply
* [RFC PATCH 09/19] pcmcia: dev_node removal (write-only drivers)
From: Dominik Brodowski @ 2010-03-21 23:07 UTC (permalink / raw)
To: linux-pcmcia
Cc: Dominik Brodowski, linux-bluetooth, Harald Welte, linux-mtd,
linux-wireless, netdev, linux-serial, alsa-devel
In-Reply-To: <20100321230617.GA24791@comet.dominikbrodowski.net>
dev_node_t was only used to transport some minor/major numbers
from the PCMCIA device drivers to deprecated userspace helpers.
However, only a few drivers made use of it, and the userspace
helpers are deprecated anyways. Therefore, get rid of dev_node_t .
As a first step, remove any usage of dev_node_t from drivers which
only wrote to this typedef/struct, but did not make use of it.
CC: linux-bluetooth@vger.kernel.org
CC: Harald Welte <laforge@gnumonks.org>
CC: linux-mtd@lists.infradead.org
CC: linux-wireless@vger.kernel.org
CC: netdev@vger.kernel.org
CC: linux-serial@vger.kernel.org
CC: alsa-devel@alsa-project.org
Signed-off-by: Dominik Brodowski <linux@dominikbrodowski.net>
---
drivers/bluetooth/bluecard_cs.c | 4 ---
drivers/bluetooth/bt3c_cs.c | 4 ---
drivers/bluetooth/btuart_cs.c | 4 ---
drivers/bluetooth/dtl1_cs.c | 4 ---
drivers/char/pcmcia/cm4040_cs.c | 5 ---
drivers/mtd/maps/pcmciamtd.c | 3 --
drivers/net/wireless/atmel_cs.c | 42 -------------------------------
drivers/net/wireless/hostap/hostap_cs.c | 9 +-----
drivers/parport/parport_cs.c | 5 ---
drivers/scsi/pcmcia/aha152x_stub.c | 3 --
drivers/scsi/pcmcia/fdomain_stub.c | 3 --
drivers/scsi/pcmcia/nsp_cs.c | 3 --
drivers/scsi/pcmcia/nsp_cs.h | 1 -
drivers/scsi/pcmcia/qlogic_stub.c | 3 --
drivers/scsi/pcmcia/sym53c500_cs.c | 3 --
drivers/serial/serial_cs.c | 9 ------
drivers/telephony/ixj_pcmcia.c | 3 --
sound/pcmcia/pdaudiocf/pdaudiocf.c | 1 -
sound/pcmcia/pdaudiocf/pdaudiocf.h | 1 -
sound/pcmcia/vx/vxpocket.c | 2 -
sound/pcmcia/vx/vxpocket.h | 1 -
21 files changed, 2 insertions(+), 111 deletions(-)
diff --git a/drivers/bluetooth/bluecard_cs.c b/drivers/bluetooth/bluecard_cs.c
index a34653d..6f907eb 100644
--- a/drivers/bluetooth/bluecard_cs.c
+++ b/drivers/bluetooth/bluecard_cs.c
@@ -65,7 +65,6 @@ MODULE_LICENSE("GPL");
typedef struct bluecard_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct hci_dev *hdev;
@@ -916,9 +915,6 @@ static int bluecard_config(struct pcmcia_device *link)
if (bluecard_open(info) != 0)
goto failed;
- strcpy(info->node.dev_name, info->hdev->name);
- link->dev_node = &info->node;
-
return 0;
failed:
diff --git a/drivers/bluetooth/bt3c_cs.c b/drivers/bluetooth/bt3c_cs.c
index 1ad9694..21e05fd 100644
--- a/drivers/bluetooth/bt3c_cs.c
+++ b/drivers/bluetooth/bt3c_cs.c
@@ -72,7 +72,6 @@ MODULE_FIRMWARE("BT3CPCC.bin");
typedef struct bt3c_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct hci_dev *hdev;
@@ -751,9 +750,6 @@ found_port:
if (bt3c_open(info) != 0)
goto failed;
- strcpy(info->node.dev_name, info->hdev->name);
- link->dev_node = &info->node;
-
return 0;
failed:
diff --git a/drivers/bluetooth/btuart_cs.c b/drivers/bluetooth/btuart_cs.c
index 1073d66..4ed7288 100644
--- a/drivers/bluetooth/btuart_cs.c
+++ b/drivers/bluetooth/btuart_cs.c
@@ -67,7 +67,6 @@ MODULE_LICENSE("GPL");
typedef struct btuart_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct hci_dev *hdev;
@@ -680,9 +679,6 @@ found_port:
if (btuart_open(info) != 0)
goto failed;
- strcpy(info->node.dev_name, info->hdev->name);
- link->dev_node = &info->node;
-
return 0;
failed:
diff --git a/drivers/bluetooth/dtl1_cs.c b/drivers/bluetooth/dtl1_cs.c
index 3d72afd..ef044d5 100644
--- a/drivers/bluetooth/dtl1_cs.c
+++ b/drivers/bluetooth/dtl1_cs.c
@@ -67,7 +67,6 @@ MODULE_LICENSE("GPL");
typedef struct dtl1_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct hci_dev *hdev;
@@ -629,9 +628,6 @@ static int dtl1_config(struct pcmcia_device *link)
if (dtl1_open(info) != 0)
goto failed;
- strcpy(info->node.dev_name, info->hdev->name);
- link->dev_node = &info->node;
-
return 0;
failed:
diff --git a/drivers/char/pcmcia/cm4040_cs.c b/drivers/char/pcmcia/cm4040_cs.c
index a6a70e4..c0775c8 100644
--- a/drivers/char/pcmcia/cm4040_cs.c
+++ b/drivers/char/pcmcia/cm4040_cs.c
@@ -72,7 +72,6 @@ static struct class *cmx_class;
struct reader_dev {
struct pcmcia_device *p_dev;
- dev_node_t node;
wait_queue_head_t devq;
wait_queue_head_t poll_wait;
wait_queue_head_t read_wait;
@@ -568,10 +567,6 @@ static int reader_config(struct pcmcia_device *link, int devno)
}
dev = link->priv;
- sprintf(dev->node.dev_name, DEVICE_NAME "%d", devno);
- dev->node.major = major;
- dev->node.minor = devno;
- dev->node.next = &dev->node;
DEBUGP(2, dev, "device " DEVICE_NAME "%d at 0x%.4x-0x%.4x\n", devno,
link->io.BasePort1, link->io.BasePort1+link->io.NumPorts1);
diff --git a/drivers/mtd/maps/pcmciamtd.c b/drivers/mtd/maps/pcmciamtd.c
index 689d6a7..87b2b8f 100644
--- a/drivers/mtd/maps/pcmciamtd.c
+++ b/drivers/mtd/maps/pcmciamtd.c
@@ -52,7 +52,6 @@ static const int debug = 0;
struct pcmciamtd_dev {
struct pcmcia_device *p_dev;
- dev_node_t node; /* device node */
caddr_t win_base; /* ioremapped address of PCMCIA window */
unsigned int win_size; /* size of window */
unsigned int offset; /* offset into card the window currently points at */
@@ -647,9 +646,7 @@ static int pcmciamtd_config(struct pcmcia_device *link)
pcmciamtd_release(link);
return -ENODEV;
}
- snprintf(dev->node.dev_name, sizeof(dev->node.dev_name), "mtd%d", mtd->index);
info("mtd%d: %s", mtd->index, mtd->name);
- link->dev_node = &dev->node;
return 0;
failed:
diff --git a/drivers/net/wireless/atmel_cs.c b/drivers/net/wireless/atmel_cs.c
index 759cdc4..c2746fc 100644
--- a/drivers/net/wireless/atmel_cs.c
+++ b/drivers/net/wireless/atmel_cs.c
@@ -85,41 +85,7 @@ static void atmel_release(struct pcmcia_device *link);
static void atmel_detach(struct pcmcia_device *p_dev);
-/*
- You'll also need to prototype all the functions that will actually
- be used to talk to your device. See 'pcmem_cs' for a good example
- of a fully self-sufficient driver; the other drivers rely more or
- less on other parts of the kernel.
-*/
-
-/*
- A linked list of "instances" of the atmelnet device. Each actual
- PCMCIA card corresponds to one device instance, and is described
- by one struct pcmcia_device structure (defined in ds.h).
-
- You may not want to use a linked list for this -- for example, the
- memory card driver uses an array of struct pcmcia_device pointers, where minor
- device numbers are used to derive the corresponding array index.
-*/
-
-/*
- A driver needs to provide a dev_node_t structure for each device
- on a card. In some cases, there is only one device per card (for
- example, ethernet cards, modems). In other cases, there may be
- many actual or logical devices (SCSI adapters, memory cards with
- multiple partitions). The dev_node_t structures need to be kept
- in a linked list starting at the 'dev' field of a struct pcmcia_device
- structure. We allocate them in the card's private data structure,
- because they generally shouldn't be allocated dynamically.
-
- In this case, we also provide a flag to indicate if a device is
- "stopped" due to a power management event, or card ejection. The
- device IO routines can use a flag like this to throttle IO to a
- card that is not ready to accept it.
-*/
-
typedef struct local_info_t {
- dev_node_t node;
struct net_device *eth_dev;
} local_info_t;
@@ -297,14 +263,6 @@ static int atmel_config(struct pcmcia_device *link)
goto failed;
- /*
- At this point, the dev_node_t structure(s) need to be
- initialized and arranged in a linked list at link->dev_node.
- */
- strcpy(dev->node.dev_name, ((local_info_t*)link->priv)->eth_dev->name );
- dev->node.major = dev->node.minor = 0;
- link->dev_node = &dev->node;
-
return 0;
failed:
diff --git a/drivers/net/wireless/hostap/hostap_cs.c b/drivers/net/wireless/hostap/hostap_cs.c
index 7e5f4c0..56d7d90 100644
--- a/drivers/net/wireless/hostap/hostap_cs.c
+++ b/drivers/net/wireless/hostap/hostap_cs.c
@@ -38,7 +38,6 @@ MODULE_PARM_DESC(ignore_cis_vcc, "Ignore broken CIS VCC entry");
/* struct local_info::hw_priv */
struct hostap_cs_priv {
- dev_node_t node;
struct pcmcia_device *link;
int sandisk_connectplus;
};
@@ -624,8 +623,6 @@ static int prism2_config(struct pcmcia_device *link)
local = iface->local;
local->hw_priv = hw_priv;
hw_priv->link = link;
- strcpy(hw_priv->node.dev_name, dev->name);
- link->dev_node = &hw_priv->node;
ret = pcmcia_request_irq(link, prism2_interrupt);
if (ret)
@@ -664,11 +661,9 @@ static int prism2_config(struct pcmcia_device *link)
sandisk_enable_wireless(dev);
ret = prism2_hw_config(dev, 1);
- if (!ret) {
+ if (!ret)
ret = hostap_hw_ready(dev);
- if (ret == 0 && local->ddev)
- strcpy(hw_priv->node.dev_name, local->ddev->name);
- }
+
return ret;
failed:
diff --git a/drivers/parport/parport_cs.c b/drivers/parport/parport_cs.c
index 80c9052..fd8cfe9 100644
--- a/drivers/parport/parport_cs.c
+++ b/drivers/parport/parport_cs.c
@@ -75,7 +75,6 @@ INT_MODULE_PARM(epp_mode, 1);
typedef struct parport_info_t {
struct pcmcia_device *p_dev;
int ndev;
- dev_node_t node;
struct parport *port;
} parport_info_t;
@@ -193,11 +192,7 @@ static int parport_config(struct pcmcia_device *link)
if (epp_mode)
p->modes |= PARPORT_MODE_TRISTATE | PARPORT_MODE_EPP;
info->ndev = 1;
- info->node.major = LP_MAJOR;
- info->node.minor = p->number;
info->port = p;
- strcpy(info->node.dev_name, p->name);
- link->dev_node = &info->node;
return 0;
diff --git a/drivers/scsi/pcmcia/aha152x_stub.c b/drivers/scsi/pcmcia/aha152x_stub.c
index c1de4ba..9d70aef 100644
--- a/drivers/scsi/pcmcia/aha152x_stub.c
+++ b/drivers/scsi/pcmcia/aha152x_stub.c
@@ -80,7 +80,6 @@ MODULE_LICENSE("Dual MPL/GPL");
typedef struct scsi_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct Scsi_Host *host;
} scsi_info_t;
@@ -185,8 +184,6 @@ static int aha152x_config_cs(struct pcmcia_device *link)
goto failed;
}
- sprintf(info->node.dev_name, "scsi%d", host->host_no);
- link->dev_node = &info->node;
info->host = host;
return 0;
diff --git a/drivers/scsi/pcmcia/fdomain_stub.c b/drivers/scsi/pcmcia/fdomain_stub.c
index 8cb6d71..21b1411 100644
--- a/drivers/scsi/pcmcia/fdomain_stub.c
+++ b/drivers/scsi/pcmcia/fdomain_stub.c
@@ -63,7 +63,6 @@ MODULE_LICENSE("Dual MPL/GPL");
typedef struct scsi_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct Scsi_Host *host;
} scsi_info_t;
@@ -155,8 +154,6 @@ static int fdomain_config(struct pcmcia_device *link)
goto failed;
scsi_scan_host(host);
- sprintf(info->node.dev_name, "scsi%d", host->host_no);
- link->dev_node = &info->node;
info->host = host;
return 0;
diff --git a/drivers/scsi/pcmcia/nsp_cs.c b/drivers/scsi/pcmcia/nsp_cs.c
index 24c78ed..0f0e112 100644
--- a/drivers/scsi/pcmcia/nsp_cs.c
+++ b/drivers/scsi/pcmcia/nsp_cs.c
@@ -1754,8 +1754,6 @@ static int nsp_cs_config(struct pcmcia_device *link)
scsi_scan_host(host);
- snprintf(info->node.dev_name, sizeof(info->node.dev_name), "scsi%d", host->host_no);
- link->dev_node = &info->node;
info->host = host;
/* Finally, report what we've done */
@@ -1813,7 +1811,6 @@ static void nsp_cs_release(struct pcmcia_device *link)
if (info->host != NULL) {
scsi_remove_host(info->host);
}
- link->dev_node = NULL;
if (link->win) {
if (data != NULL) {
diff --git a/drivers/scsi/pcmcia/nsp_cs.h b/drivers/scsi/pcmcia/nsp_cs.h
index 8c61a4f..d68c9f2 100644
--- a/drivers/scsi/pcmcia/nsp_cs.h
+++ b/drivers/scsi/pcmcia/nsp_cs.h
@@ -224,7 +224,6 @@
typedef struct scsi_info_t {
struct pcmcia_device *p_dev;
struct Scsi_Host *host;
- dev_node_t node;
int stop;
} scsi_info_t;
diff --git a/drivers/scsi/pcmcia/qlogic_stub.c b/drivers/scsi/pcmcia/qlogic_stub.c
index c3a4428..f0fc6ba 100644
--- a/drivers/scsi/pcmcia/qlogic_stub.c
+++ b/drivers/scsi/pcmcia/qlogic_stub.c
@@ -82,7 +82,6 @@ static struct scsi_host_template qlogicfas_driver_template = {
typedef struct scsi_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct Scsi_Host *host;
unsigned short manf_id;
} scsi_info_t;
@@ -235,8 +234,6 @@ static int qlogic_config(struct pcmcia_device * link)
goto failed;
}
- sprintf(info->node.dev_name, "scsi%d", host->host_no);
- link->dev_node = &info->node;
info->host = host;
return 0;
diff --git a/drivers/scsi/pcmcia/sym53c500_cs.c b/drivers/scsi/pcmcia/sym53c500_cs.c
index 6eacf4c..a511641 100644
--- a/drivers/scsi/pcmcia/sym53c500_cs.c
+++ b/drivers/scsi/pcmcia/sym53c500_cs.c
@@ -191,7 +191,6 @@
struct scsi_info_t {
struct pcmcia_device *p_dev;
- dev_node_t node;
struct Scsi_Host *host;
unsigned short manf_id;
};
@@ -792,8 +791,6 @@ SYM53C500_config(struct pcmcia_device *link)
*/
data->fast_pio = USE_FAST_PIO;
- sprintf(info->node.dev_name, "scsi%d", host->host_no);
- link->dev_node = &info->node;
info->host = host;
if (scsi_add_host(host, NULL))
diff --git a/drivers/serial/serial_cs.c b/drivers/serial/serial_cs.c
index 7519d27..048bd89 100644
--- a/drivers/serial/serial_cs.c
+++ b/drivers/serial/serial_cs.c
@@ -89,7 +89,6 @@ struct serial_info {
int manfid;
int prodid;
int c950ctrl;
- dev_node_t node[4];
int line[4];
const struct serial_quirk *quirk;
};
@@ -280,8 +279,6 @@ static void serial_remove(struct pcmcia_device *link)
for (i = 0; i < info->ndev; i++)
serial8250_unregister_port(info->line[i]);
- info->p_dev->dev_node = NULL;
-
if (!info->slave)
pcmcia_disable_device(link);
}
@@ -401,11 +398,6 @@ static int setup_serial(struct pcmcia_device *handle, struct serial_info * info,
}
info->line[info->ndev] = line;
- sprintf(info->node[info->ndev].dev_name, "ttyS%d", line);
- info->node[info->ndev].major = TTY_MAJOR;
- info->node[info->ndev].minor = 0x40 + line;
- if (info->ndev > 0)
- info->node[info->ndev - 1].next = &info->node[info->ndev];
info->ndev++;
return 0;
@@ -702,7 +694,6 @@ static int serial_config(struct pcmcia_device * link)
if (info->quirk->post(link))
goto failed;
- link->dev_node = &info->node[0];
return 0;
failed:
diff --git a/drivers/telephony/ixj_pcmcia.c b/drivers/telephony/ixj_pcmcia.c
index d442fd3..99cb224 100644
--- a/drivers/telephony/ixj_pcmcia.c
+++ b/drivers/telephony/ixj_pcmcia.c
@@ -22,7 +22,6 @@
typedef struct ixj_info_t {
int ndev;
- dev_node_t node;
struct ixj *port;
} ixj_info_t;
@@ -155,8 +154,6 @@ static int ixj_config(struct pcmcia_device * link)
j = ixj_pcmcia_probe(link->io.BasePort1, link->io.BasePort1 + 0x10);
info->ndev = 1;
- info->node.major = PHONE_MAJOR;
- link->dev_node = &info->node;
ixj_get_serial(link, j);
return 0;
diff --git a/sound/pcmcia/pdaudiocf/pdaudiocf.c b/sound/pcmcia/pdaudiocf/pdaudiocf.c
index 60fddf3..df110df 100644
--- a/sound/pcmcia/pdaudiocf/pdaudiocf.c
+++ b/sound/pcmcia/pdaudiocf/pdaudiocf.c
@@ -234,7 +234,6 @@ static int pdacf_config(struct pcmcia_device *link)
if (snd_pdacf_assign_resources(pdacf, link->io.BasePort1, link->irq) < 0)
goto failed;
- link->dev_node = &pdacf->node;
return 0;
failed:
diff --git a/sound/pcmcia/pdaudiocf/pdaudiocf.h b/sound/pcmcia/pdaudiocf/pdaudiocf.h
index b060183..a0a7ec6 100644
--- a/sound/pcmcia/pdaudiocf/pdaudiocf.h
+++ b/sound/pcmcia/pdaudiocf/pdaudiocf.h
@@ -117,7 +117,6 @@ struct snd_pdacf {
/* pcmcia stuff */
struct pcmcia_device *p_dev;
- dev_node_t node;
};
static inline void pdacf_reg_write(struct snd_pdacf *chip, unsigned char reg, unsigned short val)
diff --git a/sound/pcmcia/vx/vxpocket.c b/sound/pcmcia/vx/vxpocket.c
index 4198395..5f21d10 100644
--- a/sound/pcmcia/vx/vxpocket.c
+++ b/sound/pcmcia/vx/vxpocket.c
@@ -210,7 +210,6 @@ static int snd_vxpocket_assign_resources(struct vx_core *chip, int port, int irq
static int vxpocket_config(struct pcmcia_device *link)
{
struct vx_core *chip = link->priv;
- struct snd_vxpocket *vxp = (struct snd_vxpocket *)chip;
int ret;
snd_printdd(KERN_DEBUG "vxpocket_config called\n");
@@ -244,7 +243,6 @@ static int vxpocket_config(struct pcmcia_device *link)
if (snd_vxpocket_assign_resources(chip, link->io.BasePort1, link->irq) < 0)
goto failed;
- link->dev_node = &vxp->node;
return 0;
failed:
diff --git a/sound/pcmcia/vx/vxpocket.h b/sound/pcmcia/vx/vxpocket.h
index 27ea002..ea4df16 100644
--- a/sound/pcmcia/vx/vxpocket.h
+++ b/sound/pcmcia/vx/vxpocket.h
@@ -43,7 +43,6 @@ struct snd_vxpocket {
/* pcmcia stuff */
struct pcmcia_device *p_dev;
- dev_node_t node;
};
extern struct snd_vx_ops snd_vxpocket_ops;
--
1.6.3.3
^ permalink raw reply related
* [RFC PATCH 07/19] pcmcia: re-work pcmcia_request_irq()
From: Dominik Brodowski @ 2010-03-21 23:07 UTC (permalink / raw)
To: linux-pcmcia
Cc: Dominik Brodowski, linux-bluetooth, netdev, linux-wireless,
linux-serial, alsa-devel, linux-usb, linux-ide
In-Reply-To: <20100321230617.GA24791@comet.dominikbrodowski.net>
Instead of the old pcmcia_request_irq() interface, drivers may now
choose between:
- calling request_irq/free_irq directly. Use the IRQ from *p_dev->irq.
- use pcmcia_request_irq(p_dev, handler_t); the PCMCIA core will
clean up automatically on calls to pcmcia_disable_device() or
device ejection.
- drivers still not capable of IRQF_SHARED (or not telling us so) may
use the deprecated pcmcia_request_exclusive_irq() for the time
being; they might receive a shared IRQ nonetheless.
CC: linux-bluetooth@vger.kernel.org
CC: netdev@vger.kernel.org
CC: linux-wireless@vger.kernel.org
CC: linux-serial@vger.kernel.org
CC: alsa-devel@alsa-project.org
CC: linux-usb@vger.kernel.org
CC: linux-ide@vger.kernel.org
Signed-off-by: Dominik Brodowski <linux@dominikbrodowski.net>
---
Documentation/pcmcia/driver-changes.txt | 10 ++
drivers/ata/pata_pcmcia.c | 6 +-
drivers/bluetooth/bluecard_cs.c | 7 +-
drivers/bluetooth/bt3c_cs.c | 7 +-
drivers/bluetooth/btuart_cs.c | 7 +-
drivers/bluetooth/dtl1_cs.c | 7 +-
drivers/char/pcmcia/ipwireless/main.c | 11 +--
drivers/char/pcmcia/synclink_cs.c | 12 +--
drivers/ide/ide-cs.c | 8 +-
drivers/isdn/hardware/avm/avm_cs.c | 17 +--
drivers/isdn/hisax/avma1_cs.c | 12 +--
drivers/isdn/hisax/elsa_cs.c | 13 +--
drivers/isdn/hisax/sedlbauer_cs.c | 23 +---
drivers/isdn/hisax/teles_cs.c | 13 +--
drivers/net/pcmcia/3c574_cs.c | 6 +-
drivers/net/pcmcia/3c589_cs.c | 7 +-
drivers/net/pcmcia/axnet_cs.c | 13 +--
drivers/net/pcmcia/com20020_cs.c | 8 +-
drivers/net/pcmcia/fmvj18x_cs.c | 10 +--
drivers/net/pcmcia/ibmtr_cs.c | 8 +-
drivers/net/pcmcia/nmclan_cs.c | 6 +-
drivers/net/pcmcia/pcnet_cs.c | 8 +-
drivers/net/pcmcia/smc91c92_cs.c | 8 +-
drivers/net/pcmcia/xirc2ps_cs.c | 7 +-
drivers/net/wireless/airo_cs.c | 25 +---
drivers/net/wireless/atmel_cs.c | 28 +----
drivers/net/wireless/b43/pcmcia.c | 5 +-
drivers/net/wireless/hostap/hostap_cs.c | 29 +----
drivers/net/wireless/libertas/if_cs.c | 21 +---
drivers/net/wireless/orinoco/orinoco_cs.c | 13 +--
drivers/net/wireless/orinoco/spectrum_cs.c | 13 +--
drivers/net/wireless/ray_cs.c | 8 +-
drivers/net/wireless/wl3501_cs.c | 8 +-
drivers/parport/parport_cs.c | 8 +-
drivers/pcmcia/ds.c | 3 +-
drivers/pcmcia/pcmcia_resource.c | 137 +++++++++-------------
drivers/scsi/pcmcia/aha152x_stub.c | 6 +-
drivers/scsi/pcmcia/fdomain_stub.c | 6 +-
drivers/scsi/pcmcia/nsp_cs.c | 20 +---
drivers/scsi/pcmcia/qlogic_stub.c | 10 +-
drivers/scsi/pcmcia/sym53c500_cs.c | 6 +-
drivers/serial/serial_cs.c | 27 ++---
drivers/ssb/main.c | 2 +-
drivers/staging/comedi/drivers/cb_das16_cs.c | 26 +---
drivers/staging/comedi/drivers/das08_cs.c | 16 +--
drivers/staging/comedi/drivers/ni_daq_700.c | 23 +---
drivers/staging/comedi/drivers/ni_daq_dio24.c | 23 +---
drivers/staging/comedi/drivers/ni_labpc_cs.c | 24 +---
drivers/staging/comedi/drivers/ni_mio_cs.c | 9 +-
drivers/staging/comedi/drivers/quatech_daqp_cs.c | 22 +---
drivers/staging/netwave/netwave_cs.c | 8 +-
drivers/staging/wavelan/wavelan_cs.c | 15 +--
drivers/staging/wlags49_h2/wl_cs.c | 9 +-
drivers/usb/host/sl811_cs.c | 18 +--
include/pcmcia/cs.h | 7 -
include/pcmcia/ds.h | 11 ++-
sound/pcmcia/pdaudiocf/pdaudiocf.c | 9 +-
sound/pcmcia/vx/vxpocket.c | 8 +-
58 files changed, 244 insertions(+), 593 deletions(-)
diff --git a/Documentation/pcmcia/driver-changes.txt b/Documentation/pcmcia/driver-changes.txt
index 446f43b..3268a9a 100644
--- a/Documentation/pcmcia/driver-changes.txt
+++ b/Documentation/pcmcia/driver-changes.txt
@@ -1,4 +1,14 @@
This file details changes in 2.6 which affect PCMCIA card driver authors:
+* New IRQ request rules (as of 2.6.35)
+ Instead of the old pcmcia_request_irq() interface, drivers may now
+ choose between:
+ - calling request_irq/free_irq directly. Use the IRQ from *p_dev->irq.
+ - use pcmcia_request_irq(p_dev, handler_t); the PCMCIA core will
+ clean up automatically on calls to pcmcia_disable_device() or
+ device ejection.
+ - drivers still not capable of IRQF_SHARED (or not telling us so) may
+ use the deprecated pcmcia_request_exclusive_irq() for the time
+ being; they might receive a shared IRQ nonetheless.
* no cs_error / CS_CHECK / CONFIG_PCMCIA_DEBUG (as of 2.6.33)
Instead of the cs_error() callback or the CS_CHECK() macro, please use
diff --git a/drivers/ata/pata_pcmcia.c b/drivers/ata/pata_pcmcia.c
index 147de2f..1336216 100644
--- a/drivers/ata/pata_pcmcia.c
+++ b/drivers/ata/pata_pcmcia.c
@@ -267,7 +267,6 @@ static int pcmcia_init_one(struct pcmcia_device *pdev)
pdev->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
pdev->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
pdev->io.IOAddrLines = 3;
- pdev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
pdev->conf.Attributes = CONF_ENABLE_IRQ;
pdev->conf.IntType = INT_MEMORY_AND_IO;
@@ -292,8 +291,7 @@ static int pcmcia_init_one(struct pcmcia_device *pdev)
}
io_base = pdev->io.BasePort1;
ctl_base = stk->ctl_base;
- ret = pcmcia_request_irq(pdev, &pdev->irq);
- if (ret)
+ if (!pdev->irq)
goto failed;
ret = pcmcia_request_configuration(pdev, &pdev->conf);
@@ -343,7 +341,7 @@ static int pcmcia_init_one(struct pcmcia_device *pdev)
}
/* activate */
- ret = ata_host_activate(host, pdev->irq.AssignedIRQ, ata_sff_interrupt,
+ ret = ata_host_activate(host, pdev->irq, ata_sff_interrupt,
IRQF_SHARED, &pcmcia_sht);
if (ret)
goto failed;
diff --git a/drivers/bluetooth/bluecard_cs.c b/drivers/bluetooth/bluecard_cs.c
index d9bf87c..a34653d 100644
--- a/drivers/bluetooth/bluecard_cs.c
+++ b/drivers/bluetooth/bluecard_cs.c
@@ -869,9 +869,6 @@ static int bluecard_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts1 = 8;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
-
- link->irq.Handler = bluecard_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -908,9 +905,9 @@ static int bluecard_config(struct pcmcia_device *link)
if (i != 0)
goto failed;
- i = pcmcia_request_irq(link, &link->irq);
+ i = pcmcia_request_irq(link, bluecard_interrupt);
if (i != 0)
- link->irq.AssignedIRQ = 0;
+ goto failed;
i = pcmcia_request_configuration(link, &link->conf);
if (i != 0)
diff --git a/drivers/bluetooth/bt3c_cs.c b/drivers/bluetooth/bt3c_cs.c
index 027cb8b..1ad9694 100644
--- a/drivers/bluetooth/bt3c_cs.c
+++ b/drivers/bluetooth/bt3c_cs.c
@@ -661,9 +661,6 @@ static int bt3c_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts1 = 8;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
-
- link->irq.Handler = bt3c_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -743,9 +740,9 @@ static int bt3c_config(struct pcmcia_device *link)
goto failed;
found_port:
- i = pcmcia_request_irq(link, &link->irq);
+ i = pcmcia_request_irq(link, &bt3c_interrupt);
if (i != 0)
- link->irq.AssignedIRQ = 0;
+ goto failed;
i = pcmcia_request_configuration(link, &link->conf);
if (i != 0)
diff --git a/drivers/bluetooth/btuart_cs.c b/drivers/bluetooth/btuart_cs.c
index 60c0953..1073d66 100644
--- a/drivers/bluetooth/btuart_cs.c
+++ b/drivers/bluetooth/btuart_cs.c
@@ -590,9 +590,6 @@ static int btuart_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts1 = 8;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
-
- link->irq.Handler = btuart_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -672,9 +669,9 @@ static int btuart_config(struct pcmcia_device *link)
goto failed;
found_port:
- i = pcmcia_request_irq(link, &link->irq);
+ i = pcmcia_request_irq(link, btuart_interrupt);
if (i != 0)
- link->irq.AssignedIRQ = 0;
+ goto failed;
i = pcmcia_request_configuration(link, &link->conf);
if (i != 0)
diff --git a/drivers/bluetooth/dtl1_cs.c b/drivers/bluetooth/dtl1_cs.c
index 1778831..3d72afd 100644
--- a/drivers/bluetooth/dtl1_cs.c
+++ b/drivers/bluetooth/dtl1_cs.c
@@ -575,9 +575,6 @@ static int dtl1_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts1 = 8;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
-
- link->irq.Handler = dtl1_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -621,9 +618,9 @@ static int dtl1_config(struct pcmcia_device *link)
if (pcmcia_loop_config(link, dtl1_confcheck, NULL) < 0)
goto failed;
- i = pcmcia_request_irq(link, &link->irq);
+ i = pcmcia_request_irq(link, dtl1_interrupt);
if (i != 0)
- link->irq.AssignedIRQ = 0;
+ goto failed;
i = pcmcia_request_configuration(link, &link->conf);
if (i != 0)
diff --git a/drivers/char/pcmcia/ipwireless/main.c b/drivers/char/pcmcia/ipwireless/main.c
index dff24da..2237890 100644
--- a/drivers/char/pcmcia/ipwireless/main.c
+++ b/drivers/char/pcmcia/ipwireless/main.c
@@ -195,9 +195,6 @@ static int config_ipwireless(struct ipw_dev *ipw)
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = ipwireless_interrupt;
-
INIT_WORK(&ipw->work_reboot, signalled_reboot_work);
ipwireless_init_hardware_v1(ipw->hardware, link->io.BasePort1,
@@ -205,8 +202,7 @@ static int config_ipwireless(struct ipw_dev *ipw)
ipw->is_v2_card, signalled_reboot_callback,
ipw);
- ret = pcmcia_request_irq(link, &link->irq);
-
+ ret = pcmcia_request_irq(link, ipwireless_interrupt);
if (ret != 0)
goto exit;
@@ -217,7 +213,7 @@ static int config_ipwireless(struct ipw_dev *ipw)
(unsigned int) link->io.BasePort1,
(unsigned int) (link->io.BasePort1 +
link->io.NumPorts1 - 1),
- (unsigned int) link->irq.AssignedIRQ);
+ (unsigned int) link->irq);
if (ipw->attr_memory && ipw->common_memory)
printk(KERN_INFO IPWIRELESS_PCCARD_NAME
": attr memory 0x%08lx-0x%08lx, common memory 0x%08lx-0x%08lx\n",
@@ -271,8 +267,6 @@ exit:
static void release_ipwireless(struct ipw_dev *ipw)
{
- pcmcia_disable_device(ipw->link);
-
if (ipw->common_memory) {
release_mem_region(ipw->request_common_memory.Base,
ipw->request_common_memory.Size);
@@ -288,7 +282,6 @@ static void release_ipwireless(struct ipw_dev *ipw)
if (ipw->attr_memory)
pcmcia_release_window(ipw->link, ipw->handle_attr_memory);
- /* Break the link with Card Services */
pcmcia_disable_device(ipw->link);
}
diff --git a/drivers/char/pcmcia/synclink_cs.c b/drivers/char/pcmcia/synclink_cs.c
index c31a0d9..027690b 100644
--- a/drivers/char/pcmcia/synclink_cs.c
+++ b/drivers/char/pcmcia/synclink_cs.c
@@ -552,10 +552,6 @@ static int mgslpc_probe(struct pcmcia_device *link)
/* Initialize the struct pcmcia_device structure */
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
link->conf.Attributes = 0;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -608,9 +604,7 @@ static int mgslpc_config(struct pcmcia_device *link)
link->conf.ConfigIndex = 8;
link->conf.Present = PRESENT_OPTION;
- link->irq.Handler = mgslpc_isr;
-
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, mgslpc_isr);
if (ret)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
@@ -618,7 +612,7 @@ static int mgslpc_config(struct pcmcia_device *link)
goto failed;
info->io_base = link->io.BasePort1;
- info->irq_level = link->irq.AssignedIRQ;
+ info->irq_level = link->irq;
/* add to linked list of devices */
sprintf(info->node.dev_name, "mgslpc0");
@@ -628,7 +622,7 @@ static int mgslpc_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x:",
info->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1+link->io.NumPorts1-1);
diff --git a/drivers/ide/ide-cs.c b/drivers/ide/ide-cs.c
index ab87e4f..afd1ab7 100644
--- a/drivers/ide/ide-cs.c
+++ b/drivers/ide/ide-cs.c
@@ -102,7 +102,6 @@ static int ide_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
link->io.IOAddrLines = 3;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -285,8 +284,7 @@ static int ide_config(struct pcmcia_device *link)
io_base = link->io.BasePort1;
ctl_base = stk->ctl_base;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
@@ -299,11 +297,11 @@ static int ide_config(struct pcmcia_device *link)
if (is_kme)
outb(0x81, ctl_base+1);
- host = idecs_register(io_base, ctl_base, link->irq.AssignedIRQ, link);
+ host = idecs_register(io_base, ctl_base, link->irq, link);
if (host == NULL && link->io.NumPorts1 == 0x20) {
outb(0x02, ctl_base + 0x10);
host = idecs_register(io_base + 0x10, ctl_base + 0x10,
- link->irq.AssignedIRQ, link);
+ link->irq, link);
}
if (host == NULL)
diff --git a/drivers/isdn/hardware/avm/avm_cs.c b/drivers/isdn/hardware/avm/avm_cs.c
index 94b796d..0d485f6 100644
--- a/drivers/isdn/hardware/avm/avm_cs.c
+++ b/drivers/isdn/hardware/avm/avm_cs.c
@@ -107,9 +107,6 @@ static int avmcs_probe(struct pcmcia_device *p_dev)
p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
p_dev->io.NumPorts2 = 0;
- /* Interrupt setup */
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
-
/* General socket configuration */
p_dev->conf.Attributes = CONF_ENABLE_IRQ;
p_dev->conf.IntType = INT_MEMORY_AND_IO;
@@ -172,7 +169,7 @@ static int avmcs_configcheck(struct pcmcia_device *p_dev,
static int avmcs_config(struct pcmcia_device *link)
{
local_info_t *dev;
- int i;
+ int i = -1;
char devname[128];
int cardtype;
int (*addcard)(unsigned int port, unsigned irq);
@@ -190,11 +187,7 @@ static int avmcs_config(struct pcmcia_device *link)
return -ENODEV;
do {
- /*
- * allocate an interrupt line
- */
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0) {
+ if (!link->irq) {
/* undo */
pcmcia_disable_device(link);
break;
@@ -249,9 +242,9 @@ static int avmcs_config(struct pcmcia_device *link)
default:
case AVM_CARDTYPE_B1: addcard = b1pcmcia_addcard_b1; break;
}
- if ((i = (*addcard)(link->io.BasePort1, link->irq.AssignedIRQ)) < 0) {
+ if ((i = (*addcard)(link->io.BasePort1, link->irq)) < 0) {
printk(KERN_ERR "avm_cs: failed to add AVM-%s-Controller at i/o %#x, irq %d\n",
- dev->node.dev_name, link->io.BasePort1, link->irq.AssignedIRQ);
+ dev->node.dev_name, link->io.BasePort1, link->irq);
avmcs_release(link);
return -ENODEV;
}
@@ -270,7 +263,7 @@ static int avmcs_config(struct pcmcia_device *link)
static void avmcs_release(struct pcmcia_device *link)
{
- b1pcmcia_delcard(link->io.BasePort1, link->irq.AssignedIRQ);
+ b1pcmcia_delcard(link->io.BasePort1, link->irq);
pcmcia_disable_device(link);
} /* avmcs_release */
diff --git a/drivers/isdn/hisax/avma1_cs.c b/drivers/isdn/hisax/avma1_cs.c
index e5deb15..96d0b5d 100644
--- a/drivers/isdn/hisax/avma1_cs.c
+++ b/drivers/isdn/hisax/avma1_cs.c
@@ -119,9 +119,6 @@ static int avma1cs_probe(struct pcmcia_device *p_dev)
p_dev->io.Attributes2 = IO_DATA_PATH_WIDTH_16;
p_dev->io.IOAddrLines = 5;
- /* Interrupt setup */
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
-
/* General socket configuration */
p_dev->conf.Attributes = CONF_ENABLE_IRQ;
p_dev->conf.IntType = INT_MEMORY_AND_IO;
@@ -177,7 +174,7 @@ static int avma1cs_configcheck(struct pcmcia_device *p_dev,
static int avma1cs_config(struct pcmcia_device *link)
{
local_info_t *dev;
- int i;
+ int i = -1;
char devname[128];
IsdnCard_t icard;
int busy = 0;
@@ -197,8 +194,7 @@ static int avma1cs_config(struct pcmcia_device *link)
/*
* allocate an interrupt line
*/
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0) {
+ if (!link->irq) {
/* undo */
pcmcia_disable_device(link);
break;
@@ -230,9 +226,9 @@ static int avma1cs_config(struct pcmcia_device *link)
}
printk(KERN_NOTICE "avma1_cs: checking at i/o %#x, irq %d\n",
- link->io.BasePort1, link->irq.AssignedIRQ);
+ link->io.BasePort1, link->irq);
- icard.para[0] = link->irq.AssignedIRQ;
+ icard.para[0] = link->irq;
icard.para[1] = link->io.BasePort1;
icard.protocol = isdnprot;
icard.typ = ISDN_CTYPE_A1_PCMCIA;
diff --git a/drivers/isdn/hisax/elsa_cs.c b/drivers/isdn/hisax/elsa_cs.c
index c9a30b1..242c434 100644
--- a/drivers/isdn/hisax/elsa_cs.c
+++ b/drivers/isdn/hisax/elsa_cs.c
@@ -136,10 +136,6 @@ static int elsa_cs_probe(struct pcmcia_device *link)
local->cardnr = -1;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -223,11 +219,8 @@ static int elsa_cs_config(struct pcmcia_device *link)
if (i != 0)
goto failed;
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0) {
- link->irq.AssignedIRQ = 0;
+ if (!link->irq)
goto failed;
- }
i = pcmcia_request_configuration(link, &link->conf);
if (i != 0)
@@ -244,7 +237,7 @@ static int elsa_cs_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x: ",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1+link->io.NumPorts1-1);
@@ -253,7 +246,7 @@ static int elsa_cs_config(struct pcmcia_device *link)
link->io.BasePort2+link->io.NumPorts2-1);
printk("\n");
- icard.para[0] = link->irq.AssignedIRQ;
+ icard.para[0] = link->irq;
icard.para[1] = link->io.BasePort1;
icard.protocol = protocol;
icard.typ = ISDN_CTYPE_ELSA_PCMCIA;
diff --git a/drivers/isdn/hisax/sedlbauer_cs.c b/drivers/isdn/hisax/sedlbauer_cs.c
index 7836ec3..967371b 100644
--- a/drivers/isdn/hisax/sedlbauer_cs.c
+++ b/drivers/isdn/hisax/sedlbauer_cs.c
@@ -143,10 +143,6 @@ static int sedlbauer_probe(struct pcmcia_device *link)
local->p_dev = link;
link->priv = local;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -227,9 +223,7 @@ static int sedlbauer_config_check(struct pcmcia_device *p_dev,
else if (dflt->vpp1.present & (1<<CISTPL_POWER_VNOM))
p_dev->conf.Vpp = dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
- /* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -313,17 +307,6 @@ static int sedlbauer_config(struct pcmcia_device *link)
goto failed;
/*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
-
- /*
This actually configures the PCMCIA socket -- setting up
the I/O windows and the interrupt mapping, and putting the
card and host interface into "Memory and IO" mode.
@@ -346,7 +329,7 @@ static int sedlbauer_config(struct pcmcia_device *link)
if (link->conf.Vpp)
printk(", Vpp %d.%d", link->conf.Vpp/10, link->conf.Vpp%10);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1+link->io.NumPorts1-1);
@@ -358,7 +341,7 @@ static int sedlbauer_config(struct pcmcia_device *link)
req->Base+req->Size-1);
printk("\n");
- icard.para[0] = link->irq.AssignedIRQ;
+ icard.para[0] = link->irq;
icard.para[1] = link->io.BasePort1;
icard.protocol = protocol;
icard.typ = ISDN_CTYPE_SEDLBAUER_PCMCIA;
diff --git a/drivers/isdn/hisax/teles_cs.c b/drivers/isdn/hisax/teles_cs.c
index b0c5976..75e075c 100644
--- a/drivers/isdn/hisax/teles_cs.c
+++ b/drivers/isdn/hisax/teles_cs.c
@@ -126,10 +126,6 @@ static int teles_probe(struct pcmcia_device *link)
local->p_dev = link;
link->priv = local;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -213,11 +209,8 @@ static int teles_cs_config(struct pcmcia_device *link)
if (i != 0)
goto cs_failed;
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0) {
- link->irq.AssignedIRQ = 0;
+ if (!link->irq)
goto cs_failed;
- }
i = pcmcia_request_configuration(link, &link->conf);
if (i != 0)
@@ -234,7 +227,7 @@ static int teles_cs_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x:",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1+link->io.NumPorts1-1);
@@ -243,7 +236,7 @@ static int teles_cs_config(struct pcmcia_device *link)
link->io.BasePort2+link->io.NumPorts2-1);
printk("\n");
- icard.para[0] = link->irq.AssignedIRQ;
+ icard.para[0] = link->irq;
icard.para[1] = link->io.BasePort1;
icard.protocol = protocol;
icard.typ = ISDN_CTYPE_TELESPCMCIA;
diff --git a/drivers/net/pcmcia/3c574_cs.c b/drivers/net/pcmcia/3c574_cs.c
index 61e33cf..839a29c 100644
--- a/drivers/net/pcmcia/3c574_cs.c
+++ b/drivers/net/pcmcia/3c574_cs.c
@@ -282,8 +282,6 @@ static int tc574_probe(struct pcmcia_device *link)
spin_lock_init(&lp->window_lock);
link->io.NumPorts1 = 32;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_16;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = &el3_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 1;
@@ -352,7 +350,7 @@ static int tc574_config(struct pcmcia_device *link)
if (i != 0)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, el3_interrupt);
if (ret)
goto failed;
@@ -360,7 +358,7 @@ static int tc574_config(struct pcmcia_device *link)
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
ioaddr = dev->base_addr;
diff --git a/drivers/net/pcmcia/3c589_cs.c b/drivers/net/pcmcia/3c589_cs.c
index 091e0b0..405d772 100644
--- a/drivers/net/pcmcia/3c589_cs.c
+++ b/drivers/net/pcmcia/3c589_cs.c
@@ -194,8 +194,7 @@ static int tc589_probe(struct pcmcia_device *link)
spin_lock_init(&lp->lock);
link->io.NumPorts1 = 16;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_16;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = &el3_interrupt;
+
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 1;
@@ -271,7 +270,7 @@ static int tc589_config(struct pcmcia_device *link)
if (i != 0)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, el3_interrupt);
if (ret)
goto failed;
@@ -279,7 +278,7 @@ static int tc589_config(struct pcmcia_device *link)
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
ioaddr = dev->base_addr;
EL3WINDOW(0);
diff --git a/drivers/net/pcmcia/axnet_cs.c b/drivers/net/pcmcia/axnet_cs.c
index 09291e6..41d2def 100644
--- a/drivers/net/pcmcia/axnet_cs.c
+++ b/drivers/net/pcmcia/axnet_cs.c
@@ -169,7 +169,6 @@ static int axnet_probe(struct pcmcia_device *link)
info = PRIV(dev);
info->p_dev = link;
link->priv = dev;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -266,12 +265,9 @@ static int try_io_port(struct pcmcia_device *link)
int j, ret;
if (link->io.NumPorts1 == 32) {
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
- if (link->io.NumPorts2 > 0) {
- /* for master/slave multifunction cards */
+ /* for master/slave multifunction cards */
+ if (link->io.NumPorts2 > 0)
link->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
- link->irq.Attributes =
- IRQ_TYPE_DYNAMIC_SHARING;
- }
} else {
/* This should be two 16-port windows */
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
@@ -337,8 +333,7 @@ static int axnet_config(struct pcmcia_device *link)
if (ret != 0)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
if (link->io.NumPorts2 == 8) {
@@ -350,7 +345,7 @@ static int axnet_config(struct pcmcia_device *link)
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
if (!get_prom(link)) {
diff --git a/drivers/net/pcmcia/com20020_cs.c b/drivers/net/pcmcia/com20020_cs.c
index 21d9c9d..278438b 100644
--- a/drivers/net/pcmcia/com20020_cs.c
+++ b/drivers/net/pcmcia/com20020_cs.c
@@ -163,7 +163,6 @@ static int com20020_probe(struct pcmcia_device *p_dev)
p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
p_dev->io.NumPorts1 = 16;
p_dev->io.IOAddrLines = 16;
- p_dev->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
p_dev->conf.Attributes = CONF_ENABLE_IRQ;
p_dev->conf.IntType = INT_MEMORY_AND_IO;
@@ -275,15 +274,14 @@ static int com20020_config(struct pcmcia_device *link)
dev_dbg(&link->dev, "got ioaddr %Xh\n", ioaddr);
dev_dbg(&link->dev, "request IRQ %d\n",
- link->irq.AssignedIRQ);
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0)
+ link->irq);
+ if (!link->irq)
{
dev_dbg(&link->dev, "requestIRQ failed totally!\n");
goto failed;
}
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
diff --git a/drivers/net/pcmcia/fmvj18x_cs.c b/drivers/net/pcmcia/fmvj18x_cs.c
index b9dc80b..31f1a03 100644
--- a/drivers/net/pcmcia/fmvj18x_cs.c
+++ b/drivers/net/pcmcia/fmvj18x_cs.c
@@ -254,10 +254,6 @@ static int fmvj18x_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 5;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = fjn_interrupt;
-
/* General socket configuration */
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -425,8 +421,6 @@ static int fmvj18x_config(struct pcmcia_device *link)
}
if (link->io.NumPorts2 != 0) {
- link->irq.Attributes =
- IRQ_TYPE_DYNAMIC_SHARING;
ret = mfc_try_io_port(link);
if (ret != 0) goto failed;
} else if (cardtype == UNGERMANN) {
@@ -437,14 +431,14 @@ static int fmvj18x_config(struct pcmcia_device *link)
if (ret)
goto failed;
}
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, fjn_interrupt);
if (ret)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
if (link->io.BasePort2 != 0) {
diff --git a/drivers/net/pcmcia/ibmtr_cs.c b/drivers/net/pcmcia/ibmtr_cs.c
index 37f4a6f..0225cdf 100644
--- a/drivers/net/pcmcia/ibmtr_cs.c
+++ b/drivers/net/pcmcia/ibmtr_cs.c
@@ -156,8 +156,6 @@ static int __devinit ibmtr_attach(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts1 = 4;
link->io.IOAddrLines = 16;
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
- link->irq.Handler = ibmtr_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.Present = PRESENT_OPTION;
@@ -238,11 +236,11 @@ static int __devinit ibmtr_config(struct pcmcia_device *link)
}
dev->base_addr = link->io.BasePort1;
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_exclusive_irq(link, ibmtr_interrupt);
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
- ti->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
+ ti->irq = link->irq;
ti->global_int_enable=GLOBAL_INT_ENABLE+((dev->irq==9) ? 2 : dev->irq);
/* Allocate the MMIO memory window */
diff --git a/drivers/net/pcmcia/nmclan_cs.c b/drivers/net/pcmcia/nmclan_cs.c
index c717b14..b779e3a 100644
--- a/drivers/net/pcmcia/nmclan_cs.c
+++ b/drivers/net/pcmcia/nmclan_cs.c
@@ -463,8 +463,6 @@ static int nmclan_probe(struct pcmcia_device *link)
link->io.NumPorts1 = 32;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 5;
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
- link->irq.Handler = mace_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 1;
@@ -652,14 +650,14 @@ static int nmclan_config(struct pcmcia_device *link)
ret = pcmcia_request_io(link, &link->io);
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_exclusive_irq(link, mace_interrupt);
if (ret)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
ioaddr = dev->base_addr;
diff --git a/drivers/net/pcmcia/pcnet_cs.c b/drivers/net/pcmcia/pcnet_cs.c
index 776cad2..22a3350 100644
--- a/drivers/net/pcmcia/pcnet_cs.c
+++ b/drivers/net/pcmcia/pcnet_cs.c
@@ -265,7 +265,6 @@ static int pcnet_probe(struct pcmcia_device *link)
info->p_dev = link;
link->priv = dev;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -489,8 +488,6 @@ static int try_io_port(struct pcmcia_device *link)
if (link->io.NumPorts2 > 0) {
/* for master/slave multifunction cards */
link->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
- link->irq.Attributes =
- IRQ_TYPE_DYNAMIC_SHARING;
}
} else {
/* This should be two 16-port windows */
@@ -560,8 +557,7 @@ static int pcnet_config(struct pcmcia_device *link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
if (link->io.NumPorts2 == 8) {
@@ -575,7 +571,7 @@ static int pcnet_config(struct pcmcia_device *link)
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
if (info->flags & HAS_MISC_REG) {
if ((if_port == 1) || (if_port == 2))
diff --git a/drivers/net/pcmcia/smc91c92_cs.c b/drivers/net/pcmcia/smc91c92_cs.c
index 5adc662..1257d10 100644
--- a/drivers/net/pcmcia/smc91c92_cs.c
+++ b/drivers/net/pcmcia/smc91c92_cs.c
@@ -329,8 +329,6 @@ static int smc91c92_probe(struct pcmcia_device *link)
link->io.NumPorts1 = 16;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 4;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = &smc_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -453,7 +451,6 @@ static int mhz_mfc_config(struct pcmcia_device *link)
link->conf.Attributes |= CONF_ENABLE_SPKR;
link->conf.Status = CCSR_AUDIO_ENA;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->io.IOAddrLines = 16;
link->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts2 = 8;
@@ -651,7 +648,6 @@ static int osi_config(struct pcmcia_device *link)
link->conf.Attributes |= CONF_ENABLE_SPKR;
link->conf.Status = CCSR_AUDIO_ENA;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->io.NumPorts1 = 64;
link->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts2 = 8;
@@ -876,7 +872,7 @@ static int smc91c92_config(struct pcmcia_device *link)
if (i)
goto config_failed;
- i = pcmcia_request_irq(link, &link->irq);
+ i = pcmcia_request_irq(link, smc_interrupt);
if (i)
goto config_failed;
i = pcmcia_request_configuration(link, &link->conf);
@@ -886,7 +882,7 @@ static int smc91c92_config(struct pcmcia_device *link)
if (smc->manfid == MANFID_MOTOROLA)
mot_config(link);
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
if ((if_port >= 0) && (if_port <= 2))
dev->if_port = if_port;
diff --git a/drivers/net/pcmcia/xirc2ps_cs.c b/drivers/net/pcmcia/xirc2ps_cs.c
index 4d1802e..c9e7d7d 100644
--- a/drivers/net/pcmcia/xirc2ps_cs.c
+++ b/drivers/net/pcmcia/xirc2ps_cs.c
@@ -555,7 +555,6 @@ xirc2ps_probe(struct pcmcia_device *link)
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 1;
- link->irq.Handler = xirc2ps_interrupt;
/* Fill in card specific entries */
dev->netdev_ops = &netdev_ops;
@@ -841,7 +840,6 @@ xirc2ps_config(struct pcmcia_device * link)
link->conf.Attributes |= CONF_ENABLE_SPKR;
link->conf.Status |= CCSR_AUDIO_ENA;
}
- link->irq.Attributes |= IRQ_TYPE_DYNAMIC_SHARING;
link->io.NumPorts2 = 8;
link->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
if (local->dingo) {
@@ -866,7 +864,6 @@ xirc2ps_config(struct pcmcia_device * link)
}
printk(KNOT_XIRC "no ports available\n");
} else {
- link->irq.Attributes |= IRQ_TYPE_DYNAMIC_SHARING;
link->io.NumPorts1 = 16;
for (ioaddr = 0x300; ioaddr < 0x400; ioaddr += 0x10) {
link->io.BasePort1 = ioaddr;
@@ -885,7 +882,7 @@ xirc2ps_config(struct pcmcia_device * link)
* Now allocate an interrupt line. Note that this does not
* actually assign a handler to the interrupt.
*/
- if ((err=pcmcia_request_irq(link, &link->irq)))
+ if ((err=pcmcia_request_irq(link, xirc2ps_interrupt)))
goto config_error;
/****************
@@ -982,7 +979,7 @@ xirc2ps_config(struct pcmcia_device * link)
printk(KNOT_XIRC "invalid if_port requested\n");
/* we can now register the device with the net subsystem */
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
if (local->dingo)
diff --git a/drivers/net/wireless/airo_cs.c b/drivers/net/wireless/airo_cs.c
index f6036fb..7867c51 100644
--- a/drivers/net/wireless/airo_cs.c
+++ b/drivers/net/wireless/airo_cs.c
@@ -132,10 +132,6 @@ static int airo_probe(struct pcmcia_device *p_dev)
dev_dbg(&p_dev->dev, "airo_attach()\n");
- /* Interrupt setup */
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- p_dev->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -212,9 +208,7 @@ static int airo_cs_config_check(struct pcmcia_device *p_dev,
else if (dflt->vpp1.present & (1<<CISTPL_POWER_VNOM))
p_dev->conf.Vpp = dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
- /* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -300,16 +294,8 @@ static int airo_config(struct pcmcia_device *link)
if (ret)
goto failed;
- /*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ if (!link->irq)
+ goto failed;
/*
This actually configures the PCMCIA socket -- setting up
@@ -320,7 +306,7 @@ static int airo_config(struct pcmcia_device *link)
if (ret)
goto failed;
((local_info_t *)link->priv)->eth_dev =
- init_airo_card(link->irq.AssignedIRQ,
+ init_airo_card(link->irq,
link->io.BasePort1, 1, &link->dev);
if (!((local_info_t *)link->priv)->eth_dev)
goto failed;
@@ -338,8 +324,7 @@ static int airo_config(struct pcmcia_device *link)
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Vpp)
printk(", Vpp %d.%d", link->conf.Vpp/10, link->conf.Vpp%10);
- if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1+link->io.NumPorts1-1);
diff --git a/drivers/net/wireless/atmel_cs.c b/drivers/net/wireless/atmel_cs.c
index 3240791..759cdc4 100644
--- a/drivers/net/wireless/atmel_cs.c
+++ b/drivers/net/wireless/atmel_cs.c
@@ -141,10 +141,6 @@ static int atmel_probe(struct pcmcia_device *p_dev)
dev_dbg(&p_dev->dev, "atmel_attach()\n");
- /* Interrupt setup */
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- p_dev->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -226,9 +222,7 @@ static int atmel_config_check(struct pcmcia_device *p_dev,
else if (dflt->vpp1.present & (1<<CISTPL_POWER_VNOM))
p_dev->conf.Vpp = dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
- /* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -278,15 +272,9 @@ static int atmel_config(struct pcmcia_device *link)
if (pcmcia_loop_config(link, atmel_config_check, NULL))
goto failed;
- /*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
+ if (!link->irq) {
+ dev_err(&link->dev, "atmel: cannot assign IRQ: check that CONFIG_ISA is set in kernel config.");
+ goto failed;
}
/*
@@ -298,14 +286,8 @@ static int atmel_config(struct pcmcia_device *link)
if (ret)
goto failed;
- if (link->irq.AssignedIRQ == 0) {
- printk(KERN_ALERT
- "atmel: cannot assign IRQ: check that CONFIG_ISA is set in kernel config.");
- goto failed;
- }
-
((local_info_t*)link->priv)->eth_dev =
- init_atmel_card(link->irq.AssignedIRQ,
+ init_atmel_card(link->irq,
link->io.BasePort1,
did ? did->driver_info : ATMEL_FW_TYPE_NONE,
&link->dev,
diff --git a/drivers/net/wireless/b43/pcmcia.c b/drivers/net/wireless/b43/pcmcia.c
index 984174b..b9ea107 100644
--- a/drivers/net/wireless/b43/pcmcia.c
+++ b/drivers/net/wireless/b43/pcmcia.c
@@ -97,10 +97,7 @@ static int __devinit b43_pcmcia_probe(struct pcmcia_device *dev)
if (res != 0)
goto err_disable;
- dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- dev->irq.Handler = NULL; /* The handler is registered later. */
- res = pcmcia_request_irq(dev, &dev->irq);
- if (res != 0)
+ if (!dev->irq)
goto err_disable;
res = pcmcia_request_configuration(dev, &dev->conf);
diff --git a/drivers/net/wireless/hostap/hostap_cs.c b/drivers/net/wireless/hostap/hostap_cs.c
index d19748d..7e5f4c0 100644
--- a/drivers/net/wireless/hostap/hostap_cs.c
+++ b/drivers/net/wireless/hostap/hostap_cs.c
@@ -555,15 +555,7 @@ static int prism2_config_check(struct pcmcia_device *p_dev,
p_dev->conf.Vpp = dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000;
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
- else if (!(p_dev->conf.Attributes & CONF_ENABLE_IRQ)) {
- /* At least Compaq WL200 does not have IRQInfo1 set,
- * but it does not work without interrupts.. */
- printk(KERN_WARNING "Config has no IRQ info, but trying to "
- "enable IRQ anyway..\n");
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
- }
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
PDEBUG(DEBUG_EXTRA, "IO window settings: cfg->io.nwin=%d "
@@ -635,18 +627,9 @@ static int prism2_config(struct pcmcia_device *link)
strcpy(hw_priv->node.dev_name, dev->name);
link->dev_node = &hw_priv->node;
- /*
- * Allocate an interrupt line. Note that this does not assign a
- * handler to the interrupt, unless the 'Handler' member of the
- * irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = prism2_interrupt;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ ret = pcmcia_request_irq(link, prism2_interrupt);
+ if (ret)
+ goto failed;
/*
* This actually configures the PCMCIA socket -- setting up
@@ -657,7 +640,7 @@ static int prism2_config(struct pcmcia_device *link)
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
/* Finally, report what we've done */
@@ -667,7 +650,7 @@ static int prism2_config(struct pcmcia_device *link)
printk(", Vpp %d.%d", link->conf.Vpp / 10,
link->conf.Vpp % 10);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1+link->io.NumPorts1-1);
diff --git a/drivers/net/wireless/libertas/if_cs.c b/drivers/net/wireless/libertas/if_cs.c
index 1f6cb58..0c99b7d 100644
--- a/drivers/net/wireless/libertas/if_cs.c
+++ b/drivers/net/wireless/libertas/if_cs.c
@@ -776,7 +776,7 @@ static void if_cs_release(struct pcmcia_device *p_dev)
lbs_deb_enter(LBS_DEB_CS);
- free_irq(p_dev->irq.AssignedIRQ, card);
+ free_irq(p_dev->irq, card);
pcmcia_disable_device(p_dev);
if (card->iobase)
ioport_unmap(card->iobase);
@@ -806,8 +806,7 @@ static int if_cs_ioprobe(struct pcmcia_device *p_dev,
p_dev->io.NumPorts1 = cfg->io.win[0].len;
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
if (cfg->io.nwin != 1) {
@@ -836,9 +835,6 @@ static int if_cs_probe(struct pcmcia_device *p_dev)
card->p_dev = p_dev;
p_dev->priv = card;
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- p_dev->irq.Handler = NULL;
-
p_dev->conf.Attributes = 0;
p_dev->conf.IntType = INT_MEMORY_AND_IO;
@@ -853,13 +849,8 @@ static int if_cs_probe(struct pcmcia_device *p_dev)
* a handler to the interrupt, unless the 'Handler' member of
* the irq structure is initialized.
*/
- if (p_dev->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(p_dev, &p_dev->irq);
- if (ret) {
- lbs_pr_err("error in pcmcia_request_irq\n");
- goto out1;
- }
- }
+ if (!p_dev->irq)
+ goto out1;
/* Initialize io access */
card->iobase = ioport_map(p_dev->io.BasePort1, p_dev->io.NumPorts1);
@@ -882,7 +873,7 @@ static int if_cs_probe(struct pcmcia_device *p_dev)
/* Finally, report what we've done */
lbs_deb_cs("irq %d, io 0x%04x-0x%04x\n",
- p_dev->irq.AssignedIRQ, p_dev->io.BasePort1,
+ p_dev->irq, p_dev->io.BasePort1,
p_dev->io.BasePort1 + p_dev->io.NumPorts1 - 1);
/*
@@ -939,7 +930,7 @@ static int if_cs_probe(struct pcmcia_device *p_dev)
priv->fw_ready = 1;
/* Now actually get the IRQ */
- ret = request_irq(p_dev->irq.AssignedIRQ, if_cs_interrupt,
+ ret = request_irq(p_dev->irq, if_cs_interrupt,
IRQF_SHARED, DRV_NAME, card);
if (ret) {
lbs_pr_err("error in request_irq\n");
diff --git a/drivers/net/wireless/orinoco/orinoco_cs.c b/drivers/net/wireless/orinoco/orinoco_cs.c
index 1d4ada1..5d29b11 100644
--- a/drivers/net/wireless/orinoco/orinoco_cs.c
+++ b/drivers/net/wireless/orinoco/orinoco_cs.c
@@ -119,10 +119,6 @@ orinoco_cs_probe(struct pcmcia_device *link)
card->p_dev = link;
link->priv = priv;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = orinoco_interrupt;
-
/* General socket configuration defaults can go here. In this
* client, we assume very little, and rely on the CIS for
* almost everything. In most clients, many details (i.e.,
@@ -258,12 +254,7 @@ orinoco_cs_config(struct pcmcia_device *link)
goto failed;
}
- /*
- * Allocate an interrupt line. Note that this does not assign
- * a handler to the interrupt, unless the 'Handler' member of
- * the irq structure is initialized.
- */
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, orinoco_interrupt);
if (ret)
goto failed;
@@ -296,7 +287,7 @@ orinoco_cs_config(struct pcmcia_device *link)
/* Register an interface with the stack */
if (orinoco_if_add(priv, link->io.BasePort1,
- link->irq.AssignedIRQ) != 0) {
+ link->irq) != 0) {
printk(KERN_ERR PFX "orinoco_if_add() failed\n");
goto failed;
}
diff --git a/drivers/net/wireless/orinoco/spectrum_cs.c b/drivers/net/wireless/orinoco/spectrum_cs.c
index 59bda24..7a8e056 100644
--- a/drivers/net/wireless/orinoco/spectrum_cs.c
+++ b/drivers/net/wireless/orinoco/spectrum_cs.c
@@ -193,10 +193,6 @@ spectrum_cs_probe(struct pcmcia_device *link)
card->p_dev = link;
link->priv = priv;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = orinoco_interrupt;
-
/* General socket configuration defaults can go here. In this
* client, we assume very little, and rely on the CIS for
* almost everything. In most clients, many details (i.e.,
@@ -332,12 +328,7 @@ spectrum_cs_config(struct pcmcia_device *link)
goto failed;
}
- /*
- * Allocate an interrupt line. Note that this does not assign
- * a handler to the interrupt, unless the 'Handler' member of
- * the irq structure is initialized.
- */
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, orinoco_interrupt);
if (ret)
goto failed;
@@ -374,7 +365,7 @@ spectrum_cs_config(struct pcmcia_device *link)
/* Register an interface with the stack */
if (orinoco_if_add(priv, link->io.BasePort1,
- link->irq.AssignedIRQ) != 0) {
+ link->irq) != 0) {
printk(KERN_ERR PFX "orinoco_if_add() failed\n");
goto failed;
}
diff --git a/drivers/net/wireless/ray_cs.c b/drivers/net/wireless/ray_cs.c
index 7f0f855..e7ed2a4 100644
--- a/drivers/net/wireless/ray_cs.c
+++ b/drivers/net/wireless/ray_cs.c
@@ -321,10 +321,6 @@ static int ray_probe(struct pcmcia_device *p_dev)
p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
p_dev->io.IOAddrLines = 5;
- /* Interrupt setup. For PCMCIA, driver takes what's given */
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- p_dev->irq.Handler = &ray_interrupt;
-
/* General socket configuration */
p_dev->conf.Attributes = CONF_ENABLE_IRQ;
p_dev->conf.IntType = INT_MEMORY_AND_IO;
@@ -417,10 +413,10 @@ static int ray_config(struct pcmcia_device *link)
/* Now allocate an interrupt line. Note that this does not
actually assign a handler to the interrupt.
*/
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, ray_interrupt);
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
/* This actually configures the PCMCIA socket -- setting up
the I/O windows and the interrupt mapping.
diff --git a/drivers/net/wireless/wl3501_cs.c b/drivers/net/wireless/wl3501_cs.c
index 7b9621d..c43f05b 100644
--- a/drivers/net/wireless/wl3501_cs.c
+++ b/drivers/net/wireless/wl3501_cs.c
@@ -1897,10 +1897,6 @@ static int wl3501_probe(struct pcmcia_device *p_dev)
p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
p_dev->io.IOAddrLines = 5;
- /* Interrupt setup */
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- p_dev->irq.Handler = wl3501_interrupt;
-
/* General socket configuration */
p_dev->conf.Attributes = CONF_ENABLE_IRQ;
p_dev->conf.IntType = INT_MEMORY_AND_IO;
@@ -1961,7 +1957,7 @@ static int wl3501_config(struct pcmcia_device *link)
/* Now allocate an interrupt line. Note that this does not actually
* assign a handler to the interrupt. */
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, wl3501_interrupt);
if (ret)
goto failed;
@@ -1972,7 +1968,7 @@ static int wl3501_config(struct pcmcia_device *link)
if (ret)
goto failed;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
SET_NETDEV_DEV(dev, &link->dev);
if (register_netdev(dev)) {
diff --git a/drivers/parport/parport_cs.c b/drivers/parport/parport_cs.c
index 7dd370f..80c9052 100644
--- a/drivers/parport/parport_cs.c
+++ b/drivers/parport/parport_cs.c
@@ -105,7 +105,6 @@ static int parport_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.Attributes2 = IO_DATA_PATH_WIDTH_8;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -174,20 +173,19 @@ static int parport_config(struct pcmcia_device *link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
goto failed;
p = parport_pc_probe_port(link->io.BasePort1, link->io.BasePort2,
- link->irq.AssignedIRQ, PARPORT_DMA_NONE,
+ link->irq, PARPORT_DMA_NONE,
&link->dev, IRQF_SHARED);
if (p == NULL) {
printk(KERN_NOTICE "parport_cs: parport_pc_probe_port() at "
"0x%3x, irq %u failed\n", link->io.BasePort1,
- link->irq.AssignedIRQ);
+ link->irq);
goto failed;
}
diff --git a/drivers/pcmcia/ds.c b/drivers/pcmcia/ds.c
index e0b1efc..74245cc 100644
--- a/drivers/pcmcia/ds.c
+++ b/drivers/pcmcia/ds.c
@@ -531,7 +531,6 @@ struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int fu
p_dev->function_config = tmp_dev->function_config;
p_dev->io = tmp_dev->io;
p_dev->irq = tmp_dev->irq;
- p_dev->irq_v = tmp_dev->irq_v;
kref_get(&p_dev->function_config->ref);
}
@@ -556,7 +555,7 @@ struct pcmcia_device *pcmcia_device_add(struct pcmcia_socket *s, unsigned int fu
dev_printk(KERN_NOTICE, &p_dev->dev,
"pcmcia: registering new device %s (IRQ: %d)\n",
- p_dev->devname, p_dev->irq_v);
+ p_dev->devname, p_dev->irq);
pcmcia_device_query(p_dev);
diff --git a/drivers/pcmcia/pcmcia_resource.c b/drivers/pcmcia/pcmcia_resource.c
index f629aac..c907a3f 100644
--- a/drivers/pcmcia/pcmcia_resource.c
+++ b/drivers/pcmcia/pcmcia_resource.c
@@ -407,41 +407,6 @@ out:
} /* pcmcia_release_io */
-static int pcmcia_release_irq(struct pcmcia_device *p_dev, irq_req_t *req)
-{
- struct pcmcia_socket *s = p_dev->socket;
- config_t *c;
- int ret = -EINVAL;
-
- mutex_lock(&s->ops_mutex);
-
- c = p_dev->function_config;
-
- if (!p_dev->_irq)
- goto out;
-
- p_dev->_irq = 0;
-
- if (c->state & CONFIG_LOCKED)
- goto out;
-
- if (s->pcmcia_irq != req->AssignedIRQ) {
- dev_dbg(&s->dev, "IRQ must match assigned one\n");
- goto out;
- }
-
- if (req->Handler)
- free_irq(req->AssignedIRQ, p_dev->priv);
-
- ret = 0;
-
-out:
- mutex_unlock(&s->ops_mutex);
-
- return ret;
-} /* pcmcia_release_irq */
-
-
int pcmcia_release_window(struct pcmcia_device *p_dev, window_handle_t wh)
{
struct pcmcia_socket *s = p_dev->socket;
@@ -679,61 +644,66 @@ out:
EXPORT_SYMBOL(pcmcia_request_io);
-/** pcmcia_request_irq
+/**
+ * pcmcia_request_irq() - attempt to request a IRQ for a PCMCIA device
*
- * Request_irq() reserves an irq for this client.
+ * pcmcia_request_irq() is a wrapper around request_irq which will allow
+ * the PCMCIA core to clean up the registration in pcmcia_disable_device().
+ * Drivers are free to use request_irq() directly, but then they need to
+ * call free_irq themselfves, too. Also, only IRQF_SHARED capable IRQ
+ * handlers are allowed.
*/
-
-int pcmcia_request_irq(struct pcmcia_device *p_dev, irq_req_t *req)
+int __must_check pcmcia_request_irq(struct pcmcia_device *p_dev,
+ irq_handler_t handler)
{
- struct pcmcia_socket *s = p_dev->socket;
- config_t *c;
- int ret = -EINVAL, irq = p_dev->irq_v;
- int type = IRQF_SHARED;
+ int ret;
- mutex_lock(&s->ops_mutex);
+ if (!p_dev->irq)
+ return -EINVAL;
- if (!(s->state & SOCKET_PRESENT)) {
- dev_dbg(&s->dev, "No card present\n");
- goto out;
- }
- c = p_dev->function_config;
- if (c->state & CONFIG_LOCKED) {
- dev_dbg(&s->dev, "Configuration is locked\n");
- goto out;
- }
+ ret = request_irq(p_dev->irq, handler, IRQF_SHARED,
+ p_dev->devname, p_dev->priv);
+ if (!ret)
+ p_dev->_irq = 1;
- if (!irq) {
- dev_dbg(&s->dev, "no IRQ available\n");
- goto out;
- }
+ return ret;
+}
+EXPORT_SYMBOL(pcmcia_request_irq);
- if (!(req->Attributes & IRQ_TYPE_DYNAMIC_SHARING)) {
- req->Attributes |= IRQ_TYPE_DYNAMIC_SHARING;
- dev_printk(KERN_WARNING, &p_dev->dev, "pcmcia: the driver "
- "needs updating to supported shared IRQ lines.\n");
- }
- if (req->Handler) {
- ret = request_irq(irq, req->Handler, type,
- p_dev->devname, p_dev->priv);
- if (ret) {
- dev_printk(KERN_INFO, &s->dev,
- "request_irq() failed\n");
- goto out;
- }
- }
+/**
+ * pcmcia_request_exclusive_irq() - attempt to request an exclusive IRQ first
+ *
+ * pcmcia_request_exclusive_irq() is a wrapper around request_irq which
+ * attempts first to request an exclusive IRQ. If it fails, it also accepts
+ * a shared IRQ, but prints out a warning. PCMCIA drivers should allow for
+ * IRQ sharing and either use request_irq directly (then they need to call
+ * free_irq themselves, too), or the pcmcia_request_irq() function.
+ */
+int __must_check
+pcmcia_request_exclusive_irq(struct pcmcia_device *p_dev, irq_handler_t handler)
+{
+ int ret;
- req->AssignedIRQ = irq;
+ if (!p_dev->irq)
+ return -EINVAL;
- p_dev->_irq = 1;
+ ret = request_irq(p_dev->irq, handler, 0, p_dev->devname, p_dev->priv);
+ if (ret) {
+ ret = pcmcia_request_irq(p_dev, handler);
+ dev_printk(KERN_WARNING, &p_dev->dev, "pcmcia: "
+ "request for exclusive IRQ could not be fulfilled.\n");
+ dev_printk(KERN_WARNING, &p_dev->dev, "pcmcia: the driver "
+ "needs updating to supported shared IRQ lines.\n");
+ }
+ if (ret)
+ dev_printk(KERN_INFO, &p_dev->dev, "request_irq() failed\n");
+ else
+ p_dev->_irq = 1;
- ret = 0;
-out:
- mutex_unlock(&s->ops_mutex);
return ret;
-} /* pcmcia_request_irq */
-EXPORT_SYMBOL(pcmcia_request_irq);
+} /* pcmcia_request_exclusive_irq */
+EXPORT_SYMBOL(pcmcia_request_exclusive_irq);
#ifdef CONFIG_PCMCIA_PROBE
@@ -777,7 +747,7 @@ static int pcmcia_setup_isa_irq(struct pcmcia_device *p_dev, int type)
p_dev);
if (!ret) {
free_irq(irq, p_dev);
- p_dev->irq_v = s->pcmcia_irq = irq;
+ p_dev->irq = s->pcmcia_irq = irq;
pcmcia_used_irq[irq]++;
break;
}
@@ -818,12 +788,12 @@ int pcmcia_setup_irq(struct pcmcia_device *p_dev)
{
struct pcmcia_socket *s = p_dev->socket;
- if (p_dev->irq_v)
+ if (p_dev->irq)
return 0;
/* already assigned? */
if (s->pcmcia_irq) {
- p_dev->irq_v = s->pcmcia_irq;
+ p_dev->irq = s->pcmcia_irq;
return 0;
}
@@ -837,7 +807,7 @@ int pcmcia_setup_irq(struct pcmcia_device *p_dev)
/* but use the PCI irq otherwise */
if (s->pci_irq) {
- p_dev->irq_v = s->pcmcia_irq = s->pci_irq;
+ p_dev->irq = s->pcmcia_irq = s->pci_irq;
return 0;
}
@@ -945,7 +915,8 @@ void pcmcia_disable_device(struct pcmcia_device *p_dev)
{
pcmcia_release_configuration(p_dev);
pcmcia_release_io(p_dev, &p_dev->io);
- pcmcia_release_irq(p_dev, &p_dev->irq);
+ if (p_dev->_irq)
+ free_irq(p_dev->irq, p_dev->priv);
if (p_dev->win)
pcmcia_release_window(p_dev, p_dev->win);
}
diff --git a/drivers/scsi/pcmcia/aha152x_stub.c b/drivers/scsi/pcmcia/aha152x_stub.c
index 528733b..c1de4ba 100644
--- a/drivers/scsi/pcmcia/aha152x_stub.c
+++ b/drivers/scsi/pcmcia/aha152x_stub.c
@@ -105,7 +105,6 @@ static int aha152x_probe(struct pcmcia_device *link)
link->io.NumPorts1 = 0x20;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 10;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.Present = PRESENT_OPTION;
@@ -160,8 +159,7 @@ static int aha152x_config_cs(struct pcmcia_device *link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
@@ -172,7 +170,7 @@ static int aha152x_config_cs(struct pcmcia_device *link)
memset(&s, 0, sizeof(s));
s.conf = "PCMCIA setup";
s.io_port = link->io.BasePort1;
- s.irq = link->irq.AssignedIRQ;
+ s.irq = link->irq;
s.scsiid = host_id;
s.reconnect = reconnect;
s.parity = parity;
diff --git a/drivers/scsi/pcmcia/fdomain_stub.c b/drivers/scsi/pcmcia/fdomain_stub.c
index 9140406..8cb6d71 100644
--- a/drivers/scsi/pcmcia/fdomain_stub.c
+++ b/drivers/scsi/pcmcia/fdomain_stub.c
@@ -88,7 +88,6 @@ static int fdomain_probe(struct pcmcia_device *link)
link->io.NumPorts1 = 0x10;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 10;
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.Present = PRESENT_OPTION;
@@ -133,8 +132,7 @@ static int fdomain_config(struct pcmcia_device *link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
@@ -144,7 +142,7 @@ static int fdomain_config(struct pcmcia_device *link)
release_region(link->io.BasePort1, link->io.NumPorts1);
/* Set configuration options for the fdomain driver */
- sprintf(str, "%d,%d", link->io.BasePort1, link->irq.AssignedIRQ);
+ sprintf(str, "%d,%d", link->io.BasePort1, link->irq);
fdomain_setup(str);
host = __fdomain_16x0_detect(&fdomain_driver_template);
diff --git a/drivers/scsi/pcmcia/nsp_cs.c b/drivers/scsi/pcmcia/nsp_cs.c
index 0212464..24c78ed 100644
--- a/drivers/scsi/pcmcia/nsp_cs.c
+++ b/drivers/scsi/pcmcia/nsp_cs.c
@@ -1563,13 +1563,6 @@ static int nsp_cs_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 10; /* not used */
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
-
- /* Interrupt handler */
- link->irq.Handler = &nspintr;
- link->irq.Attributes |= IRQF_SHARED;
-
/* General socket configuration */
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -1646,8 +1639,7 @@ static int nsp_cs_config_check(struct pcmcia_device *p_dev,
}
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -1720,10 +1712,8 @@ static int nsp_cs_config(struct pcmcia_device *link)
if (ret)
goto cs_failed;
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- if (pcmcia_request_irq(link, &link->irq))
- goto cs_failed;
- }
+ if (pcmcia_request_irq(link, nspintr))
+ goto cs_failed;
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
@@ -1741,7 +1731,7 @@ static int nsp_cs_config(struct pcmcia_device *link)
/* Set port and IRQ */
data->BaseAddress = link->io.BasePort1;
data->NumAddress = link->io.NumPorts1;
- data->IrqNumber = link->irq.AssignedIRQ;
+ data->IrqNumber = link->irq;
nsp_dbg(NSP_DEBUG_INIT, "I/O[0x%x+0x%x] IRQ %d",
data->BaseAddress, data->NumAddress, data->IrqNumber);
@@ -1775,7 +1765,7 @@ static int nsp_cs_config(struct pcmcia_device *link)
printk(", Vpp %d.%d", link->conf.Vpp/10, link->conf.Vpp%10);
}
if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
}
if (link->io.NumPorts1) {
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
diff --git a/drivers/scsi/pcmcia/qlogic_stub.c b/drivers/scsi/pcmcia/qlogic_stub.c
index f85f094..c3a4428 100644
--- a/drivers/scsi/pcmcia/qlogic_stub.c
+++ b/drivers/scsi/pcmcia/qlogic_stub.c
@@ -161,7 +161,6 @@ static int qlogic_probe(struct pcmcia_device *link)
link->io.NumPorts1 = 16;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 10;
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.Present = PRESENT_OPTION;
@@ -209,8 +208,7 @@ static int qlogic_config(struct pcmcia_device * link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
@@ -227,10 +225,10 @@ static int qlogic_config(struct pcmcia_device * link)
/* The KXL-810AN has a bigger IO port window */
if (link->io.NumPorts1 == 32)
host = qlogic_detect(&qlogicfas_driver_template, link,
- link->io.BasePort1 + 16, link->irq.AssignedIRQ);
+ link->io.BasePort1 + 16, link->irq);
else
host = qlogic_detect(&qlogicfas_driver_template, link,
- link->io.BasePort1, link->irq.AssignedIRQ);
+ link->io.BasePort1, link->irq);
if (!host) {
printk(KERN_INFO "%s: no SCSI devices found\n", qlogic_name);
@@ -258,7 +256,7 @@ static void qlogic_release(struct pcmcia_device *link)
scsi_remove_host(info->host);
- free_irq(link->irq.AssignedIRQ, info->host);
+ free_irq(link->irq, info->host);
pcmcia_disable_device(link);
scsi_host_put(info->host);
diff --git a/drivers/scsi/pcmcia/sym53c500_cs.c b/drivers/scsi/pcmcia/sym53c500_cs.c
index e7564d8..6eacf4c 100644
--- a/drivers/scsi/pcmcia/sym53c500_cs.c
+++ b/drivers/scsi/pcmcia/sym53c500_cs.c
@@ -719,8 +719,7 @@ SYM53C500_config(struct pcmcia_device *link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
+ if (!link->irq)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
@@ -752,7 +751,7 @@ SYM53C500_config(struct pcmcia_device *link)
* 0x320, 0x330, 0x340, 0x350
*/
port_base = link->io.BasePort1;
- irq_level = link->irq.AssignedIRQ;
+ irq_level = link->irq;
DEB(printk("SYM53C500: port_base=0x%x, irq=%d, fast_pio=%d\n",
port_base, irq_level, USE_FAST_PIO);)
@@ -866,7 +865,6 @@ SYM53C500_probe(struct pcmcia_device *link)
link->io.NumPorts1 = 16;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.IOAddrLines = 10;
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
diff --git a/drivers/serial/serial_cs.c b/drivers/serial/serial_cs.c
index e91db4b..7519d27 100644
--- a/drivers/serial/serial_cs.c
+++ b/drivers/serial/serial_cs.c
@@ -334,7 +334,6 @@ static int serial_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.NumPorts1 = 8;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->conf.Attributes = CONF_ENABLE_IRQ;
if (do_sound) {
link->conf.Attributes |= CONF_ENABLE_SPKR;
@@ -477,7 +476,7 @@ static int simple_config(struct pcmcia_device *link)
}
if (info->slave) {
return setup_serial(link, info, port,
- link->irq.AssignedIRQ);
+ link->irq);
}
}
@@ -498,10 +497,6 @@ static int simple_config(struct pcmcia_device *link)
return -1;
found_port:
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0)
- link->irq.AssignedIRQ = 0;
-
if (info->multi && (info->manfid == MANFID_3COM))
link->conf.ConfigIndex &= ~(0x08);
@@ -514,7 +509,7 @@ found_port:
i = pcmcia_request_configuration(link, &link->conf);
if (i != 0)
return -1;
- return setup_serial(link, info, link->io.BasePort1, link->irq.AssignedIRQ);
+ return setup_serial(link, info, link->io.BasePort1, link->irq);
}
static int multi_config_check(struct pcmcia_device *p_dev,
@@ -577,13 +572,9 @@ static int multi_config(struct pcmcia_device *link)
}
}
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0) {
- /* FIXME: comment does not fit, error handling does not fit */
- printk(KERN_NOTICE
- "serial_cs: no usable port range found, giving up\n");
- link->irq.AssignedIRQ = 0;
- }
+ if (!link->irq)
+ dev_warn(&link->dev,
+ "serial_cs: no usable IRQ found, continuing...\n");
/*
* Apply any configuration quirks.
@@ -606,11 +597,11 @@ static int multi_config(struct pcmcia_device *link)
if (link->conf.ConfigIndex == 1 ||
link->conf.ConfigIndex == 3) {
err = setup_serial(link, info, base2,
- link->irq.AssignedIRQ);
+ link->irq);
base2 = link->io.BasePort1;
} else {
err = setup_serial(link, info, link->io.BasePort1,
- link->irq.AssignedIRQ);
+ link->irq);
}
info->c950ctrl = base2;
@@ -624,10 +615,10 @@ static int multi_config(struct pcmcia_device *link)
return 0;
}
- setup_serial(link, info, link->io.BasePort1, link->irq.AssignedIRQ);
+ setup_serial(link, info, link->io.BasePort1, link->irq);
for (i = 0; i < info->multi - 1; i++)
setup_serial(link, info, base2 + (8 * i),
- link->irq.AssignedIRQ);
+ link->irq);
return 0;
}
diff --git a/drivers/ssb/main.c b/drivers/ssb/main.c
index 03dfd27..1f0bddb 100644
--- a/drivers/ssb/main.c
+++ b/drivers/ssb/main.c
@@ -489,7 +489,7 @@ static int ssb_devices_register(struct ssb_bus *bus)
break;
case SSB_BUSTYPE_PCMCIA:
#ifdef CONFIG_SSB_PCMCIAHOST
- sdev->irq = bus->host_pcmcia->irq.AssignedIRQ;
+ sdev->irq = bus->host_pcmcia->irq;
dev->parent = &bus->host_pcmcia->dev;
#endif
break;
diff --git a/drivers/staging/comedi/drivers/cb_das16_cs.c b/drivers/staging/comedi/drivers/cb_das16_cs.c
index bc375e7..7711036 100644
--- a/drivers/staging/comedi/drivers/cb_das16_cs.c
+++ b/drivers/staging/comedi/drivers/cb_das16_cs.c
@@ -179,12 +179,12 @@ static int das16cs_attach(struct comedi_device *dev,
}
printk("\n");
- ret = request_irq(link->irq.AssignedIRQ, das16cs_interrupt,
+ ret = request_irq(link->irq, das16cs_interrupt,
IRQF_SHARED, "cb_das16_cs", dev);
if (ret < 0) {
return ret;
}
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
printk("irq=%u ", dev->irq);
dev->board_ptr = das16cs_probe(dev, link);
@@ -701,10 +701,6 @@ static int das16cs_pcmcia_attach(struct pcmcia_device *link)
link->priv = local;
/* Initialize the pcmcia_device structure */
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
link->conf.Attributes = 0;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -739,8 +735,7 @@ static int das16cs_pcmcia_config_loop(struct pcmcia_device *p_dev,
return -EINVAL;
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -779,16 +774,9 @@ static void das16cs_pcmcia_config(struct pcmcia_device *link)
goto failed;
}
- /*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ if (!link->irq)
+ goto failed;
+
/*
This actually configures the PCMCIA socket -- setting up
the I/O windows and the interrupt mapping, and putting the
@@ -810,7 +798,7 @@ static void das16cs_pcmcia_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %u", link->irq.AssignedIRQ);
+ printk(", irq %u", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1 + link->io.NumPorts1 - 1);
diff --git a/drivers/staging/comedi/drivers/das08_cs.c b/drivers/staging/comedi/drivers/das08_cs.c
index f12ef1c..906cc2a 100644
--- a/drivers/staging/comedi/drivers/das08_cs.c
+++ b/drivers/staging/comedi/drivers/das08_cs.c
@@ -171,10 +171,6 @@ static int das08_pcmcia_attach(struct pcmcia_device *link)
local->link = link;
link->priv = local;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
- link->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -228,8 +224,7 @@ static int das08_pcmcia_config_loop(struct pcmcia_device *p_dev,
return -ENODEV;
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -276,11 +271,8 @@ static void das08_pcmcia_config(struct pcmcia_device *link)
goto failed;
}
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ if (!link->irq)
+ goto failed;
/*
This actually configures the PCMCIA socket -- setting up
@@ -303,7 +295,7 @@ static void das08_pcmcia_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %u", link->irq.AssignedIRQ);
+ printk(", irq %u", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1 + link->io.NumPorts1 - 1);
diff --git a/drivers/staging/comedi/drivers/ni_daq_700.c b/drivers/staging/comedi/drivers/ni_daq_700.c
index c9b0395..04fa19a 100644
--- a/drivers/staging/comedi/drivers/ni_daq_700.c
+++ b/drivers/staging/comedi/drivers/ni_daq_700.c
@@ -379,7 +379,7 @@ static int dio700_attach(struct comedi_device *dev, struct comedi_devconfig *it)
return -EIO;
iobase = link->io.BasePort1;
#ifdef incomplete
- irq = link->irq.AssignedIRQ;
+ irq = link->irq;
#endif
break;
default:
@@ -501,10 +501,6 @@ static int dio700_cs_attach(struct pcmcia_device *link)
local->link = link;
link->priv = local;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -576,8 +572,7 @@ static int dio700_pcmcia_config_loop(struct pcmcia_device *p_dev,
}
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -638,16 +633,8 @@ static void dio700_config(struct pcmcia_device *link)
goto failed;
}
- /*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ if (!link->irq)
+ goto failed;
/*
This actually configures the PCMCIA socket -- setting up
@@ -670,7 +657,7 @@ static void dio700_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1 + link->io.NumPorts1 - 1);
diff --git a/drivers/staging/comedi/drivers/ni_daq_dio24.c b/drivers/staging/comedi/drivers/ni_daq_dio24.c
index 9017be3..4b0c608 100644
--- a/drivers/staging/comedi/drivers/ni_daq_dio24.c
+++ b/drivers/staging/comedi/drivers/ni_daq_dio24.c
@@ -130,7 +130,7 @@ static int dio24_attach(struct comedi_device *dev, struct comedi_devconfig *it)
return -EIO;
iobase = link->io.BasePort1;
#ifdef incomplete
- irq = link->irq.AssignedIRQ;
+ irq = link->irq;
#endif
break;
default:
@@ -252,10 +252,6 @@ static int dio24_cs_attach(struct pcmcia_device *link)
local->link = link;
link->priv = local;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -327,8 +323,7 @@ static int dio24_pcmcia_config_loop(struct pcmcia_device *p_dev,
}
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -389,16 +384,8 @@ static void dio24_config(struct pcmcia_device *link)
goto failed;
}
- /*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ if (!link->irq)
+ goto failed;
/*
This actually configures the PCMCIA socket -- setting up
@@ -421,7 +408,7 @@ static void dio24_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1 + link->io.NumPorts1 - 1);
diff --git a/drivers/staging/comedi/drivers/ni_labpc_cs.c b/drivers/staging/comedi/drivers/ni_labpc_cs.c
index 5a0e5b9..53caa78 100644
--- a/drivers/staging/comedi/drivers/ni_labpc_cs.c
+++ b/drivers/staging/comedi/drivers/ni_labpc_cs.c
@@ -143,7 +143,7 @@ static int labpc_attach(struct comedi_device *dev, struct comedi_devconfig *it)
if (!link)
return -EIO;
iobase = link->io.BasePort1;
- irq = link->irq.AssignedIRQ;
+ irq = link->irq;
break;
default:
printk("bug! couldn't determine board type\n");
@@ -228,10 +228,6 @@ static int labpc_cs_attach(struct pcmcia_device *link)
local->link = link;
link->priv = local;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = NULL;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -305,9 +301,7 @@ static int labpc_pcmcia_config_loop(struct pcmcia_device *p_dev,
}
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |=
- (CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ);
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -367,16 +361,8 @@ static void labpc_config(struct pcmcia_device *link)
goto failed;
}
- /*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ if (!link->irq)
+ goto failed;
/*
This actually configures the PCMCIA socket -- setting up
@@ -399,7 +385,7 @@ static void labpc_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1 + link->io.NumPorts1 - 1);
diff --git a/drivers/staging/comedi/drivers/ni_mio_cs.c b/drivers/staging/comedi/drivers/ni_mio_cs.c
index dc4849a..a6007ab 100644
--- a/drivers/staging/comedi/drivers/ni_mio_cs.c
+++ b/drivers/staging/comedi/drivers/ni_mio_cs.c
@@ -272,7 +272,6 @@ static int cs_attach(struct pcmcia_device *link)
{
link->io.Attributes1 = IO_DATA_PATH_WIDTH_16;
link->io.NumPorts1 = 16;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -344,10 +343,8 @@ static void mio_cs_config(struct pcmcia_device *link)
return;
}
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret) {
- printk("pcmcia_request_irq() returned error: %i\n", ret);
- }
+ if (!link->irq)
+ dev_info(&link->dev, "no IRQ available\n");
ret = pcmcia_request_configuration(link, &link->conf);
@@ -369,7 +366,7 @@ static int mio_cs_attach(struct comedi_device *dev, struct comedi_devconfig *it)
dev->driver = &driver_ni_mio_cs;
dev->iobase = link->io.BasePort1;
- irq = link->irq.AssignedIRQ;
+ irq = link->irq;
printk("comedi%d: %s: DAQCard: io 0x%04lx, irq %u, ",
dev->minor, dev->driver->driver_name, dev->iobase, irq);
diff --git a/drivers/staging/comedi/drivers/quatech_daqp_cs.c b/drivers/staging/comedi/drivers/quatech_daqp_cs.c
index 3325f24..7aa17f9 100644
--- a/drivers/staging/comedi/drivers/quatech_daqp_cs.c
+++ b/drivers/staging/comedi/drivers/quatech_daqp_cs.c
@@ -1040,10 +1040,6 @@ static int daqp_cs_attach(struct pcmcia_device *link)
local->link = link;
link->priv = local;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = daqp_interrupt;
-
/*
General socket configuration defaults can go here. In this
client, we assume very little, and rely on the CIS for almost
@@ -1105,8 +1101,7 @@ static int daqp_pcmcia_config_loop(struct pcmcia_device *p_dev,
return -ENODEV;
/* Do we need to allocate an interrupt? */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -1144,16 +1139,9 @@ static void daqp_cs_config(struct pcmcia_device *link)
goto failed;
}
- /*
- Allocate an interrupt line. Note that this does not assign a
- handler to the interrupt, unless the 'Handler' member of the
- irq structure is initialized.
- */
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- }
+ ret = pcmcia_request_irq(link, daqp_interrupt);
+ if (ret)
+ goto failed;
/*
This actually configures the PCMCIA socket -- setting up
@@ -1180,7 +1168,7 @@ static void daqp_cs_config(struct pcmcia_device *link)
printk(KERN_INFO "%s: index 0x%02x",
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Attributes & CONF_ENABLE_IRQ)
- printk(", irq %u", link->irq.AssignedIRQ);
+ printk(", irq %u", link->irq);
if (link->io.NumPorts1)
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1 + link->io.NumPorts1 - 1);
diff --git a/drivers/staging/netwave/netwave_cs.c b/drivers/staging/netwave/netwave_cs.c
index 26477fd..1206b9c 100644
--- a/drivers/staging/netwave/netwave_cs.c
+++ b/drivers/staging/netwave/netwave_cs.c
@@ -382,10 +382,6 @@ static int netwave_probe(struct pcmcia_device *link)
link->io.Attributes2 = IO_DATA_PATH_WIDTH_16; */
link->io.IOAddrLines = 5;
- /* Interrupt setup */
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- link->irq.Handler = &netwave_interrupt;
-
/* General socket configuration */
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
@@ -732,7 +728,7 @@ static int netwave_pcmcia_config(struct pcmcia_device *link) {
* Now allocate an interrupt line. Note that this does not
* actually assign a handler to the interrupt.
*/
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_irq(link, netwave_interrupt);
if (ret)
goto failed;
@@ -767,7 +763,7 @@ static int netwave_pcmcia_config(struct pcmcia_device *link) {
ramBase = ioremap(req.Base, 0x8000);
priv->ramBase = ramBase;
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
SET_NETDEV_DEV(dev, &link->dev);
diff --git a/drivers/staging/wavelan/wavelan_cs.c b/drivers/staging/wavelan/wavelan_cs.c
index 04f691d..37fa855 100644
--- a/drivers/staging/wavelan/wavelan_cs.c
+++ b/drivers/staging/wavelan/wavelan_cs.c
@@ -3850,12 +3850,8 @@ wv_pcmcia_config(struct pcmcia_device * link)
if (i != 0)
break;
- /*
- * Now allocate an interrupt line. Note that this does not
- * actually assign a handler to the interrupt.
- */
- i = pcmcia_request_irq(link, &link->irq);
- if (i != 0)
+ i = pcmcia_request_interrupt(link, wavelan_interrupt);
+ if (!i)
break;
/*
@@ -3890,7 +3886,7 @@ wv_pcmcia_config(struct pcmcia_device * link)
break;
/* Feed device with this info... */
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
netif_start_queue(dev);
@@ -4437,10 +4433,6 @@ wavelan_probe(struct pcmcia_device *p_dev)
p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
p_dev->io.IOAddrLines = 3;
- /* Interrupt setup */
- p_dev->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING;
- p_dev->irq.Handler = wavelan_interrupt;
-
/* General socket configuration */
p_dev->conf.Attributes = CONF_ENABLE_IRQ;
p_dev->conf.IntType = INT_MEMORY_AND_IO;
@@ -4487,7 +4479,6 @@ wavelan_probe(struct pcmcia_device *p_dev)
ret = wv_hw_config(dev);
if (ret) {
- dev->irq = 0;
pcmcia_disable_device(p_dev);
return ret;
}
diff --git a/drivers/staging/wlags49_h2/wl_cs.c b/drivers/staging/wlags49_h2/wl_cs.c
index 811a8da..b2eb158 100644
--- a/drivers/staging/wlags49_h2/wl_cs.c
+++ b/drivers/staging/wlags49_h2/wl_cs.c
@@ -157,15 +157,12 @@ static int wl_adapter_attach(struct pcmcia_device *link)
link->io.NumPorts1 = HCF_NUM_IO_PORTS;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_16;
link->io.IOAddrLines = 6;
- link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING | IRQ_HANDLE_PRESENT;
- link->irq.IRQInfo1 = IRQ_INFO2_VALID | IRQ_LEVEL_ID;
- link->irq.Handler = &wl_isr;
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 5;
link->conf.Present = PRESENT_OPTION;
- link->priv = link->irq.Instance = dev;
+ link->priv = dev;
lp = wl_priv(dev);
lp->link = link;
@@ -319,11 +316,11 @@ void wl_adapter_insert( struct pcmcia_device *link )
link->conf.Attributes |= CONF_ENABLE_IRQ;
CS_CHECK(RequestIO, pcmcia_request_io(link, &link->io));
- CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq));
+ CS_CHECK(RequestIRQ, pcmcia_request_irq(link, wl_isr));
CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf));
- dev->irq = link->irq.AssignedIRQ;
+ dev->irq = link->irq;
dev->base_addr = link->io.BasePort1;
SET_NETDEV_DEV(dev, &handle_to_dev(link));
diff --git a/drivers/usb/host/sl811_cs.c b/drivers/usb/host/sl811_cs.c
index 39d253e..a712788 100644
--- a/drivers/usb/host/sl811_cs.c
+++ b/drivers/usb/host/sl811_cs.c
@@ -163,8 +163,7 @@ static int sl811_cs_config_check(struct pcmcia_device *p_dev,
dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
/* we need an interrupt */
- if (cfg->irq.IRQInfo1 || dflt->irq.IRQInfo1)
- p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
+ p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
/* IO window settings */
p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
@@ -197,11 +196,8 @@ static int sl811_cs_config(struct pcmcia_device *link)
/* require an IRQ and two registers */
if (!link->io.NumPorts1 || link->io.NumPorts1 < 2)
goto failed;
- if (link->conf.Attributes & CONF_ENABLE_IRQ) {
- ret = pcmcia_request_irq(link, &link->irq);
- if (ret)
- goto failed;
- } else
+
+ if (!link->irq)
goto failed;
ret = pcmcia_request_configuration(link, &link->conf);
@@ -216,12 +212,12 @@ static int sl811_cs_config(struct pcmcia_device *link)
dev->node.dev_name, link->conf.ConfigIndex);
if (link->conf.Vpp)
printk(", Vpp %d.%d", link->conf.Vpp/10, link->conf.Vpp%10);
- printk(", irq %d", link->irq.AssignedIRQ);
+ printk(", irq %d", link->irq);
printk(", io 0x%04x-0x%04x", link->io.BasePort1,
link->io.BasePort1+link->io.NumPorts1-1);
printk("\n");
- if (sl811_hc_init(parent, link->io.BasePort1, link->irq.AssignedIRQ)
+ if (sl811_hc_init(parent, link->io.BasePort1, link->irq)
< 0) {
failed:
printk(KERN_WARNING "sl811_cs_config failed\n");
@@ -241,10 +237,6 @@ static int sl811_cs_probe(struct pcmcia_device *link)
local->p_dev = link;
link->priv = local;
- /* Initialize */
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
- link->irq.Handler = NULL;
-
link->conf.Attributes = 0;
link->conf.IntType = INT_MEMORY_AND_IO;
diff --git a/include/pcmcia/cs.h b/include/pcmcia/cs.h
index af61571..a04e6ca 100644
--- a/include/pcmcia/cs.h
+++ b/include/pcmcia/cs.h
@@ -114,13 +114,6 @@ typedef struct io_req_t {
#define IO_DATA_PATH_WIDTH_16 0x08
#define IO_DATA_PATH_WIDTH_AUTO 0x10
-/* For RequestIRQ and ReleaseIRQ */
-typedef struct irq_req_t {
- u_int Attributes;
- u_int AssignedIRQ;
- irq_handler_t Handler;
-} irq_req_t;
-
/* Attributes for RequestIRQ and ReleaseIRQ */
#define IRQ_TYPE 0x03
#define IRQ_TYPE_EXCLUSIVE 0x00
diff --git a/include/pcmcia/ds.h b/include/pcmcia/ds.h
index f70c5c1..81b6d86 100644
--- a/include/pcmcia/ds.h
+++ b/include/pcmcia/ds.h
@@ -90,12 +90,11 @@ struct pcmcia_device {
dev_node_t *dev_node;
u_int open;
io_req_t io;
- irq_req_t irq;
config_req_t conf;
window_handle_t win;
/* device setup */
- unsigned int irq_v; /* do not use directly yet */
+ unsigned int irq;
/* Is the device suspended, or in the process of
* being removed? */
@@ -195,7 +194,13 @@ int pcmcia_access_configuration_register(struct pcmcia_device *p_dev,
/* device configuration */
int pcmcia_request_io(struct pcmcia_device *p_dev, io_req_t *req);
-int pcmcia_request_irq(struct pcmcia_device *p_dev, irq_req_t *req);
+
+int __must_check __deprecated
+pcmcia_request_exclusive_irq(struct pcmcia_device *p_dev,
+ irq_handler_t handler);
+int __must_check pcmcia_request_irq(struct pcmcia_device *p_dev,
+ irq_handler_t handler);
+
int pcmcia_request_configuration(struct pcmcia_device *p_dev,
config_req_t *req);
diff --git a/sound/pcmcia/pdaudiocf/pdaudiocf.c b/sound/pcmcia/pdaudiocf/pdaudiocf.c
index dcf8539..60fddf3 100644
--- a/sound/pcmcia/pdaudiocf/pdaudiocf.c
+++ b/sound/pcmcia/pdaudiocf/pdaudiocf.c
@@ -142,11 +142,6 @@ static int snd_pdacf_probe(struct pcmcia_device *link)
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.NumPorts1 = 16;
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
- /* FIXME: This driver should be updated to allow for dynamic IRQ sharing */
- /* link->irq.Attributes = IRQ_TYPE_DYNAMIC_SHARING; */
-
- link->irq.Handler = pdacf_interrupt;
link->conf.Attributes = CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 1;
@@ -228,7 +223,7 @@ static int pdacf_config(struct pcmcia_device *link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_exclusive_irq(link, pdacf_interrupt);
if (ret)
goto failed;
@@ -236,7 +231,7 @@ static int pdacf_config(struct pcmcia_device *link)
if (ret)
goto failed;
- if (snd_pdacf_assign_resources(pdacf, link->io.BasePort1, link->irq.AssignedIRQ) < 0)
+ if (snd_pdacf_assign_resources(pdacf, link->io.BasePort1, link->irq) < 0)
goto failed;
link->dev_node = &pdacf->node;
diff --git a/sound/pcmcia/vx/vxpocket.c b/sound/pcmcia/vx/vxpocket.c
index 7be3b33..4198395 100644
--- a/sound/pcmcia/vx/vxpocket.c
+++ b/sound/pcmcia/vx/vxpocket.c
@@ -161,10 +161,6 @@ static int snd_vxpocket_new(struct snd_card *card, int ibl,
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
link->io.NumPorts1 = 16;
- link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
-
- link->irq.Handler = &snd_vx_irq_handler;
-
link->conf.Attributes = CONF_ENABLE_IRQ;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 1;
@@ -234,7 +230,7 @@ static int vxpocket_config(struct pcmcia_device *link)
if (ret)
goto failed;
- ret = pcmcia_request_irq(link, &link->irq);
+ ret = pcmcia_request_exclusive_irq(link, snd_vx_irq_handler);
if (ret)
goto failed;
@@ -245,7 +241,7 @@ static int vxpocket_config(struct pcmcia_device *link)
chip->dev = &link->dev;
snd_card_set_dev(chip->card, chip->dev);
- if (snd_vxpocket_assign_resources(chip, link->io.BasePort1, link->irq.AssignedIRQ) < 0)
+ if (snd_vxpocket_assign_resources(chip, link->io.BasePort1, link->irq) < 0)
goto failed;
link->dev_node = &vxp->node;
--
1.6.3.3
^ permalink raw reply related
* Re: HCI_MAX_DEV is a bit too small.
From: Peter Dons Tychsen @ 2010-03-21 22:26 UTC (permalink / raw)
To: Marcel Holtmann; +Cc: linux-bluetooth
In-Reply-To: <1268619078.6278.10.camel@donpedro>
Hello again,
> > So I could be convinced to add new functions to read/write the limit
> > from within an application itself. So that it can be changed without
> > re-compiling the library. Feel free to propose a patch.
> I will see what i can do. What is needed is probably a
> hci_set_max_devices() call. Then hcitool could call that with the number
> of devices needed.
After some time looking at it more closely, i can see that the real
problem is not in hcilib, but in the stack itself. The real problem is
that there is no way of getting the actual number of devices with
reading out all of them... and thereby allocating space for MAX devices
(which could be endless). Chicken and Egg situation. What is really
needed is an ioctl to get the current count. This could be done by:
a) A new IOCTL called HCIGETDEVCOUNT that returns the device count.
or
b) Modifying HCIGETDEVLIST to return the device count (dev_num) if the
input count (dev_num) is zero (without actually returning the devices).
This would be backward compatible, as zero is not a valid input today.
Is any of this acceptable? Please advise what solutions could be
acceptable.
This would allow for hci_for_each_dev (and in turn the stack via IOCTL)
to use less resources, and to support more devices. This could deprecate
the need for MAX_HCI_DEV altogether, as it is not used anywhere else in
the lib. There is of-course allot of other software using that constant,
but maybe removing it over time would be good. It gives the user of the
lib a false idea of a non-existing limitation.
Thanks,
/Pedro
^ permalink raw reply
* RE: [bluetooth-next V3] Bluetooth: handle device reset event
From: Marcel Holtmann @ 2010-03-21 5:48 UTC (permalink / raw)
To: Winkler, Tomas
Cc: linux-bluetooth@vger.kernel.org, Cohen, Guy, Rindjunsky, Ron,
Paskar, Gregory
In-Reply-To: <6F5C1D715B2DA5498A628E6B9C124F04016C304710@hasmsx504.ger.corp.intel.com>
Hi Tomas,
> > > A Bluetooth device experiencing hardware failure may issue
> > > a HARDWARE_ERROR hci event. The reaction to this event is device
> > > reset flow implemented in following sequence.
> > >
> > > 1. Notify: HCI_DEV_DOWN
> > > 2. Reinitialize internal structures.
> > > 3. Call driver flush function
> > > 4. Send HCI reset request to the device.
> > > 5. Send HCI init sequence reset to the device.
> > > 6. Notify HCI_DEV_UP.
> > >
> > > Signed-off-by: Gregory Paskar <gregory.paskar@intel.com>
> > > Signed-off-by: Tomas Winkler <tomas.winkler@intel.com>
> > > Reviewed-by: Ron Rindjunsky <ron.rindjunsky@intel.com>
> > > ---
> > > V2:
> > > 1. Fix email typo
> > > 2. Fix style issues
> > > V3:
> > > 1. align with naming convention hw_err_work -> work_hw_err
> > > 2. use per controller workqueue
> > >
> > > include/net/bluetooth/hci.h | 5 ++++
> > > include/net/bluetooth/hci_core.h | 2 +
> > > net/bluetooth/hci_core.c | 47
> > +++++++++++++++++++++++++++++++++++++-
> > > net/bluetooth/hci_event.c | 3 ++
> > > 4 files changed, 56 insertions(+), 1 deletions(-)
> > >
> > > diff --git a/include/net/bluetooth/hci.h b/include/net/bluetooth/hci.h
> > > index fc0c502..3f986e7 100644
> > > --- a/include/net/bluetooth/hci.h
> > > +++ b/include/net/bluetooth/hci.h
> > > @@ -695,6 +695,11 @@ struct hci_ev_cmd_status {
> > > __le16 opcode;
> > > } __attribute__ ((packed));
> > >
> > > +#define HCI_EV_HARDWARE_ERROR 0x10
> > > +struct hci_ev_hw_error {
> > > + __u8 hw_code;
> > > +} __attribute__ ((packed));
> > > +
> >
> > So the rule is that the HCI_EV and hci_ev struct names are matching up.
> > It should be matching what we have in the library (not a hard
> > requirement though):
> >
> > #define EVT_HARDWARE_ERROR 0x10
> > typedef struct {
> > uint8_t code;
> > } __attribute__ ((packed)) evt_hardware_error;
> >
> > So just spell it out hardware_error. This means it is also code and not
> > hw_code inside the struct.
> >
> > > #define HCI_EV_ROLE_CHANGE 0x12
> > > struct hci_ev_role_change {
> > > __u8 status;
> > > diff --git a/include/net/bluetooth/hci_core.h
> > b/include/net/bluetooth/hci_core.h
> > > index e17849e..1c9601d 100644
> > > --- a/include/net/bluetooth/hci_core.h
> > > +++ b/include/net/bluetooth/hci_core.h
> > > @@ -113,6 +113,8 @@ struct hci_dev {
> > > struct tasklet_struct rx_task;
> > > struct tasklet_struct tx_task;
> > >
> > > + struct work_struct work_hw_err;
> > > +
> >
> > I would prefer if you just call it reset_work actually. I know that we
> > are acting on a hardware error, but the action that we are performing is
> > actually a full reset. It might be useful for other parts of the stack
> > as well.
> >
> > > struct sk_buff_head rx_q;
> > > struct sk_buff_head raw_q;
> > > struct sk_buff_head cmd_q;
> > > diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c
> > > index 8b4baac..c5a43e3 100644
> > > --- a/net/bluetooth/hci_core.c
> > > +++ b/net/bluetooth/hci_core.c
> > > @@ -839,6 +839,51 @@ static int hci_rfkill_set_block(void *data, bool
> > blocked)
> > > return 0;
> > > }
> > >
> > > +static void hci_device_hw_error(struct hci_dev *hdev)
> > > +{
> > > + hci_req_lock(hdev);
> > > +
> > > + /* notify: going down */
> > > + clear_bit(HCI_UP, &hdev->flags);
> > > + hci_notify(hdev, HCI_DEV_DOWN);
> > > +
> > > + tasklet_disable(&hdev->tx_task);
> > > + skb_queue_purge(&hdev->rx_q);
> > > + skb_queue_purge(&hdev->cmd_q);
> > > +
> > > + hci_dev_lock_bh(hdev);
> > > + inquiry_cache_flush(hdev);
> > > + hci_conn_hash_flush(hdev);
> > > + hci_dev_unlock_bh(hdev);
> > > +
> > > + if (hdev->flush)
> > > + hdev->flush(hdev);
> > > +
> > > + /* reset device */
> > > + atomic_set(&hdev->cmd_cnt, 1);
> > > + hdev->acl_cnt = 0;
> > > + hdev->sco_cnt = 0;
> > > + hci_reset_req(hdev, 0);
> > > +
> > > + /* init device */
> > > + atomic_set(&hdev->cmd_cnt, 1);
> > > + hci_init_req(hdev, 0);
> > > +
> > > + tasklet_enable(&hdev->tx_task);
> > > +
> > > + /* notify: going back up */
> > > + set_bit(HCI_UP, &hdev->flags);
> > > + hci_notify(hdev, HCI_DEV_UP);
> > > +
> > > + hci_req_unlock(hdev);
> > > +}
> > > +
> > > +static void hci_work_hw_err(struct work_struct *ws)
> > > +{
> > > + struct hci_dev *hdev = container_of(ws, struct hci_dev, work_hw_err);
> > > + hci_device_hw_error(hdev);
> > > +}
> > > +
> >
> > Please name it hci_reset_work to match it properly. And then put
> > everything in the same function. No need to really split it here.
> >
> > What I would prefer if we can split out the open/close code and re-use
> > it it here.
> >
> > > static const struct rfkill_ops hci_rfkill_ops = {
> > > .set_block = hci_rfkill_set_block,
> > > };
> > > @@ -908,7 +953,7 @@ int hci_register_dev(struct hci_dev *hdev)
> > > tasklet_init(&hdev->cmd_task, hci_cmd_task,(unsigned long) hdev);
> > > tasklet_init(&hdev->rx_task, hci_rx_task, (unsigned long) hdev);
> > > tasklet_init(&hdev->tx_task, hci_tx_task, (unsigned long) hdev);
> > > -
> > > + INIT_WORK(&hdev->work_hw_err, hci_work_hw_err);
> > > skb_queue_head_init(&hdev->rx_q);
> > > skb_queue_head_init(&hdev->cmd_q);
> > > skb_queue_head_init(&hdev->raw_q);
> >
> > I am missing the cancel_work_sync() call in hci_unregister_dev().
> >
> > > diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c
> > > index 6c57fc7..6bcf3e9 100644
> > > --- a/net/bluetooth/hci_event.c
> > > +++ b/net/bluetooth/hci_event.c
> > > @@ -1955,6 +1955,9 @@ void hci_event_packet(struct hci_dev *hdev, struct
> > sk_buff *skb)
> > > case HCI_EV_REMOTE_HOST_FEATURES:
> > > hci_remote_host_features_evt(hdev, skb);
> > > break;
> > > + case HCI_EV_HARDWARE_ERROR:
> > > + queue_work(hdev->workqueue, &hdev->work_hw_err);
> > > + break;
> > >
> > > default:
> > > BT_DBG("%s event 0x%x", hdev->name, event);
> >
> > Since it seems you have the only hardware where this can be re-produced,
> > it would be great if you include some hcidump -X -V extracts inside the
> > commit message.
> >
>
> What exactly are you looking for? I'm testing it by artificially triggering the error. Does hci dump has any value in that case?
you mentioned that you see hardware error events on real hardware. I
like to see the hcidump from that actually.
And btw. the bluetooth-testing tree now contains the patches to push
event processing into a workqueue. They have limit testing so far, but
seems to work fine. Someone still needs to do some performance testing
before we can clear that patch for upstream. However it should make your
reset logic patch a lot simpler.
Regards
Marcel
^ permalink raw reply
* RE: [bluetooth-next V3] Bluetooth: handle device reset event
From: Winkler, Tomas @ 2010-03-19 23:03 UTC (permalink / raw)
To: Marcel Holtmann
Cc: linux-bluetooth@vger.kernel.org, Cohen, Guy, Rindjunsky, Ron,
Paskar, Gregory
In-Reply-To: <1268976778.3003.14.camel@violet>
DQoNCj4gLS0tLS1PcmlnaW5hbCBNZXNzYWdlLS0tLS0NCj4gRnJvbTogTWFyY2VsIEhvbHRtYW5u
IFttYWlsdG86bWFyY2VsQGhvbHRtYW5uLm9yZ10NCj4gU2VudDogRnJpZGF5LCBNYXJjaCAxOSwg
MjAxMCA3OjMzIEFNDQo+IFRvOiBXaW5rbGVyLCBUb21hcw0KPiBDYzogbGludXgtYmx1ZXRvb3Ro
QHZnZXIua2VybmVsLm9yZzsgQ29oZW4sIEd1eTsgUmluZGp1bnNreSwgUm9uOyBQYXNrYXIsDQo+
IEdyZWdvcnkNCj4gU3ViamVjdDogUmU6IFtibHVldG9vdGgtbmV4dCBWM10gQmx1ZXRvb3RoOiBo
YW5kbGUgZGV2aWNlIHJlc2V0IGV2ZW50DQo+IA0KPiBIaSBUb21hcywNCj4gDQo+ID4gRnJvbTog
R3JlZ29yeSBQYXNrYXIgPGdyZWdvcnkucGFza2FyQGludGVsLmNvbT4NCj4gPg0KPiA+IEEgQmx1
ZXRvb3RoIGRldmljZSBleHBlcmllbmNpbmcgaGFyZHdhcmUgZmFpbHVyZSBtYXkgaXNzdWUNCj4g
PiBhIEhBUkRXQVJFX0VSUk9SIGhjaSBldmVudC4gVGhlIHJlYWN0aW9uIHRvIHRoaXMgZXZlbnQg
aXMgZGV2aWNlDQo+ID4gcmVzZXQgZmxvdyBpbXBsZW1lbnRlZCBpbiBmb2xsb3dpbmcgc2VxdWVu
Y2UuDQo+ID4NCj4gPiAxLiBOb3RpZnk6IEhDSV9ERVZfRE9XTg0KPiA+IDIuIFJlaW5pdGlhbGl6
ZSBpbnRlcm5hbCBzdHJ1Y3R1cmVzLg0KPiA+IDMuIENhbGwgZHJpdmVyIGZsdXNoIGZ1bmN0aW9u
DQo+ID4gNC4gU2VuZCBIQ0kgcmVzZXQgcmVxdWVzdCB0byB0aGUgZGV2aWNlLg0KPiA+IDUuIFNl
bmQgSENJIGluaXQgc2VxdWVuY2UgcmVzZXQgdG8gdGhlIGRldmljZS4NCj4gPiA2LiBOb3RpZnkg
SENJX0RFVl9VUC4NCj4gPg0KPiA+IFNpZ25lZC1vZmYtYnk6IEdyZWdvcnkgUGFza2FyIDxncmVn
b3J5LnBhc2thckBpbnRlbC5jb20+DQo+ID4gU2lnbmVkLW9mZi1ieTogVG9tYXMgV2lua2xlciA8
dG9tYXMud2lua2xlckBpbnRlbC5jb20+DQo+ID4gUmV2aWV3ZWQtYnk6IFJvbiBSaW5kanVuc2t5
IDxyb24ucmluZGp1bnNreUBpbnRlbC5jb20+DQo+ID4gLS0tDQo+ID4gVjI6DQo+ID4gMS4gRml4
IGVtYWlsIHR5cG8NCj4gPiAyLiBGaXggc3R5bGUgaXNzdWVzDQo+ID4gVjM6DQo+ID4gMS4gYWxp
Z24gd2l0aCBuYW1pbmcgY29udmVudGlvbiBod19lcnJfd29yayAtPiB3b3JrX2h3X2Vycg0KPiA+
IDIuIHVzZSBwZXIgY29udHJvbGxlciB3b3JrcXVldWUNCj4gPg0KPiA+ICBpbmNsdWRlL25ldC9i
bHVldG9vdGgvaGNpLmggICAgICB8ICAgIDUgKysrKw0KPiA+ICBpbmNsdWRlL25ldC9ibHVldG9v
dGgvaGNpX2NvcmUuaCB8ICAgIDIgKw0KPiA+ICBuZXQvYmx1ZXRvb3RoL2hjaV9jb3JlLmMgICAg
ICAgICB8ICAgNDcNCj4gKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKy0NCj4g
PiAgbmV0L2JsdWV0b290aC9oY2lfZXZlbnQuYyAgICAgICAgfCAgICAzICsrDQo+ID4gIDQgZmls
ZXMgY2hhbmdlZCwgNTYgaW5zZXJ0aW9ucygrKSwgMSBkZWxldGlvbnMoLSkNCj4gPg0KPiA+IGRp
ZmYgLS1naXQgYS9pbmNsdWRlL25ldC9ibHVldG9vdGgvaGNpLmggYi9pbmNsdWRlL25ldC9ibHVl
dG9vdGgvaGNpLmgNCj4gPiBpbmRleCBmYzBjNTAyLi4zZjk4NmU3IDEwMDY0NA0KPiA+IC0tLSBh
L2luY2x1ZGUvbmV0L2JsdWV0b290aC9oY2kuaA0KPiA+ICsrKyBiL2luY2x1ZGUvbmV0L2JsdWV0
b290aC9oY2kuaA0KPiA+IEBAIC02OTUsNiArNjk1LDExIEBAIHN0cnVjdCBoY2lfZXZfY21kX3N0
YXR1cyB7DQo+ID4gIAlfX2xlMTYgICBvcGNvZGU7DQo+ID4gIH0gX19hdHRyaWJ1dGVfXyAoKHBh
Y2tlZCkpOw0KPiA+DQo+ID4gKyNkZWZpbmUgSENJX0VWX0hBUkRXQVJFX0VSUk9SIDB4MTANCj4g
PiArc3RydWN0IGhjaV9ldl9od19lcnJvciB7DQo+ID4gKwlfX3U4ICAgICBod19jb2RlOw0KPiA+
ICt9IF9fYXR0cmlidXRlX18gKChwYWNrZWQpKTsNCj4gPiArDQo+IA0KPiBTbyB0aGUgcnVsZSBp
cyB0aGF0IHRoZSBIQ0lfRVYgYW5kIGhjaV9ldiBzdHJ1Y3QgbmFtZXMgYXJlIG1hdGNoaW5nIHVw
Lg0KPiBJdCBzaG91bGQgYmUgbWF0Y2hpbmcgd2hhdCB3ZSBoYXZlIGluIHRoZSBsaWJyYXJ5IChu
b3QgYSBoYXJkDQo+IHJlcXVpcmVtZW50IHRob3VnaCk6DQo+IA0KPiAjZGVmaW5lIEVWVF9IQVJE
V0FSRV9FUlJPUiAgICAgICAgICAgICAgMHgxMA0KPiB0eXBlZGVmIHN0cnVjdCB7DQo+ICAgICAg
ICAgdWludDhfdCAgICAgICAgIGNvZGU7DQo+IH0gX19hdHRyaWJ1dGVfXyAoKHBhY2tlZCkpIGV2
dF9oYXJkd2FyZV9lcnJvcjsNCj4gDQo+IFNvIGp1c3Qgc3BlbGwgaXQgb3V0IGhhcmR3YXJlX2Vy
cm9yLiBUaGlzIG1lYW5zIGl0IGlzIGFsc28gY29kZSBhbmQgbm90DQo+IGh3X2NvZGUgaW5zaWRl
IHRoZSBzdHJ1Y3QuDQo+IA0KPiA+ICAjZGVmaW5lIEhDSV9FVl9ST0xFX0NIQU5HRQkJMHgxMg0K
PiA+ICBzdHJ1Y3QgaGNpX2V2X3JvbGVfY2hhbmdlIHsNCj4gPiAgCV9fdTggICAgIHN0YXR1czsN
Cj4gPiBkaWZmIC0tZ2l0IGEvaW5jbHVkZS9uZXQvYmx1ZXRvb3RoL2hjaV9jb3JlLmgNCj4gYi9p
bmNsdWRlL25ldC9ibHVldG9vdGgvaGNpX2NvcmUuaA0KPiA+IGluZGV4IGUxNzg0OWUuLjFjOTYw
MWQgMTAwNjQ0DQo+ID4gLS0tIGEvaW5jbHVkZS9uZXQvYmx1ZXRvb3RoL2hjaV9jb3JlLmgNCj4g
PiArKysgYi9pbmNsdWRlL25ldC9ibHVldG9vdGgvaGNpX2NvcmUuaA0KPiA+IEBAIC0xMTMsNiAr
MTEzLDggQEAgc3RydWN0IGhjaV9kZXYgew0KPiA+ICAJc3RydWN0IHRhc2tsZXRfc3RydWN0CXJ4
X3Rhc2s7DQo+ID4gIAlzdHJ1Y3QgdGFza2xldF9zdHJ1Y3QJdHhfdGFzazsNCj4gPg0KPiA+ICsJ
c3RydWN0IHdvcmtfc3RydWN0CXdvcmtfaHdfZXJyOw0KPiA+ICsNCj4gDQo+IEkgd291bGQgcHJl
ZmVyIGlmIHlvdSBqdXN0IGNhbGwgaXQgcmVzZXRfd29yayBhY3R1YWxseS4gSSBrbm93IHRoYXQg
d2UNCj4gYXJlIGFjdGluZyBvbiBhIGhhcmR3YXJlIGVycm9yLCBidXQgdGhlIGFjdGlvbiB0aGF0
IHdlIGFyZSBwZXJmb3JtaW5nIGlzDQo+IGFjdHVhbGx5IGEgZnVsbCByZXNldC4gSXQgbWlnaHQg
YmUgdXNlZnVsIGZvciBvdGhlciBwYXJ0cyBvZiB0aGUgc3RhY2sNCj4gYXMgd2VsbC4NCj4gDQo+
ID4gIAlzdHJ1Y3Qgc2tfYnVmZl9oZWFkCXJ4X3E7DQo+ID4gIAlzdHJ1Y3Qgc2tfYnVmZl9oZWFk
CXJhd19xOw0KPiA+ICAJc3RydWN0IHNrX2J1ZmZfaGVhZAljbWRfcTsNCj4gPiBkaWZmIC0tZ2l0
IGEvbmV0L2JsdWV0b290aC9oY2lfY29yZS5jIGIvbmV0L2JsdWV0b290aC9oY2lfY29yZS5jDQo+
ID4gaW5kZXggOGI0YmFhYy4uYzVhNDNlMyAxMDA2NDQNCj4gPiAtLS0gYS9uZXQvYmx1ZXRvb3Ro
L2hjaV9jb3JlLmMNCj4gPiArKysgYi9uZXQvYmx1ZXRvb3RoL2hjaV9jb3JlLmMNCj4gPiBAQCAt
ODM5LDYgKzgzOSw1MSBAQCBzdGF0aWMgaW50IGhjaV9yZmtpbGxfc2V0X2Jsb2NrKHZvaWQgKmRh
dGEsIGJvb2wNCj4gYmxvY2tlZCkNCj4gPiAgCXJldHVybiAwOw0KPiA+ICB9DQo+ID4NCj4gPiAr
c3RhdGljIHZvaWQgaGNpX2RldmljZV9od19lcnJvcihzdHJ1Y3QgaGNpX2RldiAqaGRldikNCj4g
PiArew0KPiA+ICsJaGNpX3JlcV9sb2NrKGhkZXYpOw0KPiA+ICsNCj4gPiArCS8qIG5vdGlmeTog
Z29pbmcgZG93biAqLw0KPiA+ICsJY2xlYXJfYml0KEhDSV9VUCwgJmhkZXYtPmZsYWdzKTsNCj4g
PiArCWhjaV9ub3RpZnkoaGRldiwgSENJX0RFVl9ET1dOKTsNCj4gPiArDQo+ID4gKwl0YXNrbGV0
X2Rpc2FibGUoJmhkZXYtPnR4X3Rhc2spOw0KPiA+ICsJc2tiX3F1ZXVlX3B1cmdlKCZoZGV2LT5y
eF9xKTsNCj4gPiArCXNrYl9xdWV1ZV9wdXJnZSgmaGRldi0+Y21kX3EpOw0KPiA+ICsNCj4gPiAr
CWhjaV9kZXZfbG9ja19iaChoZGV2KTsNCj4gPiArCWlucXVpcnlfY2FjaGVfZmx1c2goaGRldik7
DQo+ID4gKwloY2lfY29ubl9oYXNoX2ZsdXNoKGhkZXYpOw0KPiA+ICsJaGNpX2Rldl91bmxvY2tf
YmgoaGRldik7DQo+ID4gKw0KPiA+ICsJaWYgKGhkZXYtPmZsdXNoKQ0KPiA+ICsJCWhkZXYtPmZs
dXNoKGhkZXYpOw0KPiA+ICsNCj4gPiArCS8qIHJlc2V0IGRldmljZSAqLw0KPiA+ICsJYXRvbWlj
X3NldCgmaGRldi0+Y21kX2NudCwgMSk7DQo+ID4gKwloZGV2LT5hY2xfY250ID0gMDsNCj4gPiAr
CWhkZXYtPnNjb19jbnQgPSAwOw0KPiA+ICsJaGNpX3Jlc2V0X3JlcShoZGV2LCAwKTsNCj4gPiAr
DQo+ID4gKwkvKiBpbml0IGRldmljZSAqLw0KPiA+ICsJYXRvbWljX3NldCgmaGRldi0+Y21kX2Nu
dCwgMSk7DQo+ID4gKwloY2lfaW5pdF9yZXEoaGRldiwgMCk7DQo+ID4gKw0KPiA+ICsJdGFza2xl
dF9lbmFibGUoJmhkZXYtPnR4X3Rhc2spOw0KPiA+ICsNCj4gPiArCS8qIG5vdGlmeTogZ29pbmcg
YmFjayB1cCAqLw0KPiA+ICsJc2V0X2JpdChIQ0lfVVAsICZoZGV2LT5mbGFncyk7DQo+ID4gKwlo
Y2lfbm90aWZ5KGhkZXYsIEhDSV9ERVZfVVApOw0KPiA+ICsNCj4gPiArCWhjaV9yZXFfdW5sb2Nr
KGhkZXYpOw0KPiA+ICt9DQo+ID4gKw0KPiA+ICtzdGF0aWMgdm9pZCBoY2lfd29ya19od19lcnIo
c3RydWN0IHdvcmtfc3RydWN0ICp3cykNCj4gPiArew0KPiA+ICsJc3RydWN0IGhjaV9kZXYgKmhk
ZXYgPSBjb250YWluZXJfb2Yod3MsIHN0cnVjdCBoY2lfZGV2LCB3b3JrX2h3X2Vycik7DQo+ID4g
KwloY2lfZGV2aWNlX2h3X2Vycm9yKGhkZXYpOw0KPiA+ICt9DQo+ID4gKw0KPiANCj4gUGxlYXNl
IG5hbWUgaXQgaGNpX3Jlc2V0X3dvcmsgdG8gbWF0Y2ggaXQgcHJvcGVybHkuIEFuZCB0aGVuIHB1
dA0KPiBldmVyeXRoaW5nIGluIHRoZSBzYW1lIGZ1bmN0aW9uLiBObyBuZWVkIHRvIHJlYWxseSBz
cGxpdCBpdCBoZXJlLg0KPiANCj4gV2hhdCBJIHdvdWxkIHByZWZlciBpZiB3ZSBjYW4gc3BsaXQg
b3V0IHRoZSBvcGVuL2Nsb3NlIGNvZGUgYW5kIHJlLXVzZQ0KPiBpdCBpdCBoZXJlLg0KPiANCj4g
PiAgc3RhdGljIGNvbnN0IHN0cnVjdCByZmtpbGxfb3BzIGhjaV9yZmtpbGxfb3BzID0gew0KPiA+
ICAJLnNldF9ibG9jayA9IGhjaV9yZmtpbGxfc2V0X2Jsb2NrLA0KPiA+ICB9Ow0KPiA+IEBAIC05
MDgsNyArOTUzLDcgQEAgaW50IGhjaV9yZWdpc3Rlcl9kZXYoc3RydWN0IGhjaV9kZXYgKmhkZXYp
DQo+ID4gIAl0YXNrbGV0X2luaXQoJmhkZXYtPmNtZF90YXNrLCBoY2lfY21kX3Rhc2ssKHVuc2ln
bmVkIGxvbmcpIGhkZXYpOw0KPiA+ICAJdGFza2xldF9pbml0KCZoZGV2LT5yeF90YXNrLCBoY2lf
cnhfdGFzaywgKHVuc2lnbmVkIGxvbmcpIGhkZXYpOw0KPiA+ICAJdGFza2xldF9pbml0KCZoZGV2
LT50eF90YXNrLCBoY2lfdHhfdGFzaywgKHVuc2lnbmVkIGxvbmcpIGhkZXYpOw0KPiA+IC0NCj4g
PiArCUlOSVRfV09SSygmaGRldi0+d29ya19od19lcnIsIGhjaV93b3JrX2h3X2Vycik7DQo+ID4g
IAlza2JfcXVldWVfaGVhZF9pbml0KCZoZGV2LT5yeF9xKTsNCj4gPiAgCXNrYl9xdWV1ZV9oZWFk
X2luaXQoJmhkZXYtPmNtZF9xKTsNCj4gPiAgCXNrYl9xdWV1ZV9oZWFkX2luaXQoJmhkZXYtPnJh
d19xKTsNCj4gDQo+IEkgYW0gbWlzc2luZyB0aGUgY2FuY2VsX3dvcmtfc3luYygpIGNhbGwgaW4g
aGNpX3VucmVnaXN0ZXJfZGV2KCkuDQo+IA0KPiA+IGRpZmYgLS1naXQgYS9uZXQvYmx1ZXRvb3Ro
L2hjaV9ldmVudC5jIGIvbmV0L2JsdWV0b290aC9oY2lfZXZlbnQuYw0KPiA+IGluZGV4IDZjNTdm
YzcuLjZiY2YzZTkgMTAwNjQ0DQo+ID4gLS0tIGEvbmV0L2JsdWV0b290aC9oY2lfZXZlbnQuYw0K
PiA+ICsrKyBiL25ldC9ibHVldG9vdGgvaGNpX2V2ZW50LmMNCj4gPiBAQCAtMTk1NSw2ICsxOTU1
LDkgQEAgdm9pZCBoY2lfZXZlbnRfcGFja2V0KHN0cnVjdCBoY2lfZGV2ICpoZGV2LCBzdHJ1Y3QN
Cj4gc2tfYnVmZiAqc2tiKQ0KPiA+ICAJY2FzZSBIQ0lfRVZfUkVNT1RFX0hPU1RfRkVBVFVSRVM6
DQo+ID4gIAkJaGNpX3JlbW90ZV9ob3N0X2ZlYXR1cmVzX2V2dChoZGV2LCBza2IpOw0KPiA+ICAJ
CWJyZWFrOw0KPiA+ICsJY2FzZSBIQ0lfRVZfSEFSRFdBUkVfRVJST1I6DQo+ID4gKwkJcXVldWVf
d29yayhoZGV2LT53b3JrcXVldWUsICZoZGV2LT53b3JrX2h3X2Vycik7DQo+ID4gKwkJYnJlYWs7
DQo+ID4NCj4gPiAgCWRlZmF1bHQ6DQo+ID4gIAkJQlRfREJHKCIlcyBldmVudCAweCV4IiwgaGRl
di0+bmFtZSwgZXZlbnQpOw0KPiANCj4gU2luY2UgaXQgc2VlbXMgeW91IGhhdmUgdGhlIG9ubHkg
aGFyZHdhcmUgd2hlcmUgdGhpcyBjYW4gYmUgcmUtcHJvZHVjZWQsDQo+IGl0IHdvdWxkIGJlIGdy
ZWF0IGlmIHlvdSBpbmNsdWRlIHNvbWUgaGNpZHVtcCAtWCAtViBleHRyYWN0cyBpbnNpZGUgdGhl
DQo+IGNvbW1pdCBtZXNzYWdlLg0KPiANCg0KV2hhdCBleGFjdGx5IGFyZSB5b3UgbG9va2luZyBm
b3I/IEknbSB0ZXN0aW5nIGl0IGJ5IGFydGlmaWNpYWxseSB0cmlnZ2VyaW5nIHRoZSBlcnJvci4g
RG9lcyBoY2kgZHVtcCBoYXMgYW55IHZhbHVlIGluIHRoYXQgY2FzZT8NCg0KVGhhbmtzDQpUb21h
cw0KLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tCkludGVsIElzcmFlbCAoNzQpIExpbWl0ZWQKClRoaXMgZS1tYWlsIGFu
ZCBhbnkgYXR0YWNobWVudHMgbWF5IGNvbnRhaW4gY29uZmlkZW50aWFsIG1hdGVyaWFsIGZvcgp0
aGUgc29sZSB1c2Ugb2YgdGhlIGludGVuZGVkIHJlY2lwaWVudChzKS4gQW55IHJldmlldyBvciBk
aXN0cmlidXRpb24KYnkgb3RoZXJzIGlzIHN0cmljdGx5IHByb2hpYml0ZWQuIElmIHlvdSBhcmUg
bm90IHRoZSBpbnRlbmRlZApyZWNpcGllbnQsIHBsZWFzZSBjb250YWN0IHRoZSBzZW5kZXIgYW5k
IGRlbGV0ZSBhbGwgY29waWVzLgo=
^ permalink raw reply
* Re: [PATCH] Bluetooth: Allow SCO/eSCO packet type selection for outgoing SCO connections.
From: smcoe1 @ 2010-03-19 18:48 UTC (permalink / raw)
To: Marcel Holtmann; +Cc: Ville Tervo, Nick Pelly, linux-bluetooth@vger.kernel.org
In-Reply-To: <35c90d961002251705j2cd95a8cjc7d10aa432a49f4@mail.gmail.com>
Hi Marcel,
On Thu, Feb 25, 2010 at 9:05 PM, Nick Pelly <npelly@google.com> wrote:
> On Sun, Feb 21, 2010 at 11:53 PM, Ville Tervo <ville.tervo@nokia.com> wrote:
>> Nick Pelly wrote:
>>>>>
>>>>> Attached is a new patch with the consistent bit logic.
>>>>>
>>>>> Comments?
>>>>
>>>> In order to keep backwards compatibility 1 should mean "don't allow this
>>>> packet type" for all packets. Other wise old application with new kernel
>>>> would not allow any packet types.
>>>
>>> The current patch achieves this backwards compatibility by assuming
>>> that all packet types are allowed if the old sockaddr_sco struct is
>>> used (it checks the size), or if sco_pkt_type is 0.
>>
>> OK. Then my concerns are gone.
>
> As best I can tell there are no objections. We're going ahead with this patch.
>
> http://android.git.kernel.org/?p=kernel/common.git;a=commit;h=3b077241e02041b1f03fee912896b8de1d7ac096
>
> Nick
Is this patch (or something similar) being considered for merging into
the bluetooth-2.6 tree. We are experiencing similar issues with these
and other car kits.
Thanks,
Steve
^ permalink raw reply
* Re: Kernel panic in rfcomm_run - unbalanced refcount on rfcomm_session
From: Andrei Emeltchenko @ 2010-03-19 8:33 UTC (permalink / raw)
To: Nick Pelly; +Cc: Ville Tervo, Dave Young, Bluettooth Linux, Marcel Holtmann
In-Reply-To: <35c90d961003082331p6798006do17d6178ae2840591@mail.gmail.com>
Hi,
On Tue, Mar 9, 2010 at 9:31 AM, Nick Pelly <npelly@google.com> wrote:
> On Mon, Mar 8, 2010 at 11:19 PM, Ville Tervo <ville.tervo@nokia.com> wrote:
>> Tervo Ville (Nokia-D/Helsinki) wrote:
>>>
>>> l2cap socket status might change while rfcomm is processing frames. And
>>> that makes rfcomm_process_rx to do double rfcomm_session_put() for incoming
>>> session reference. We cannot use sk_state.
>>>
>>> Could you try with this patch if it helps to your problems also? My OPP
>>> problems went away with this patch.
>>>
>>> I moved rfcomm_session_put() for incoming session to rfcomm_session_close
>>> in order to get more clear _hold()/_put() pairs.
>>>
>>>
>>
>> Any comments about the patch in previous mail?
>
> Your patch looks sane to me, although I know enough of the Bluez
> rfcomm state machine to know that I don't know it that well :)
We have tested this patch and it looks to be working. Shall we apply it?
Regards,
Andrei
^ permalink raw reply
* Re: [PATCH] Bluetooth: Fix kernel crash on BT stress tests.
From: Andrei Emeltchenko @ 2010-03-19 8:31 UTC (permalink / raw)
To: Gustavo F. Padovan; +Cc: linux-bluetooth, marcel
In-Reply-To: <20100315150203.GA31186@vigoh>
[-- Attachment #1: Type: text/plain, Size: 3905 bytes --]
Hi,
On Mon, Mar 15, 2010 at 5:05 PM, Gustavo F. Padovan <gustavo@padovan.org> wrote:
> * Andrei Emeltchenko <andrei.emeltchenko.news@gmail.com> [2010-03-15 12:57:18 +0200]:
>
>> Hi Gustavo
>>
>> On Fri, Mar 12, 2010 at 12:41 AM, Gustavo F. Padovan
>> <padovan@profusion.mobi> wrote:
>> > Hi Andrei,
>> >
>> > * Andrei Emeltchenko <andrei.emeltchenko.news@gmail.com> [2010-02-16 12:36:47 +0200]:
>> >
>> >> From 0135f732cb45e5e91062aca84a61a40b172200a4 Mon Sep 17 00:00:00 2001
>> >> From: Andrei Emeltchenko <andrei.emeltchenko@nokia.com>
>> >> Date: Tue, 16 Feb 2010 10:52:33 +0200
>> >> Subject: [PATCH] Bluetooth: Fix kernel crash on BT stress tests.
>> >>
>> >> Added very simple check that req buffer has enough space to
>> >> fit configuration parameters. Shall be enough to reject packets
>> >> with configuration size more than req buffer.
>> >>
>> >> Crash trace below
>> >>
>> >> [ 6069.659393] Unable to handle kernel paging request at virtual
>> >> address 02000205
>> >> [ 6069.673034] Internal error: Oops: 805 [#1] PREEMPT
>> >> ...
>> >> [ 6069.727172] PC is at l2cap_add_conf_opt+0x70/0xf0 [l2cap]
>> >> [ 6069.732604] LR is at l2cap_recv_frame+0x1350/0x2e78 [l2cap]
>> >> ...
>> >> [ 6070.030303] Backtrace:
>> >> [ 6070.032806] [<bf1c2880>] (l2cap_add_conf_opt+0x0/0xf0 [l2cap]) from
>> >> [<bf1c6624>] (l2cap_recv_frame+0x1350/0x2e78 [l2cap])
>> >> [ 6070.043823] r8:dc5d3100 r7:df2a91d6 r6:00000001 r5:df2a8000 r4:00000200
>> >> [ 6070.050659] [<bf1c52d4>] (l2cap_recv_frame+0x0/0x2e78 [l2cap]) from
>> >> [<bf1c8408>] (l2cap_recv_acldata+0x2bc/0x350 [l2cap])
>> >> [ 6070.061798] [<bf1c814c>] (l2cap_recv_acldata+0x0/0x350 [l2cap]) from
>> >> [<bf0037a4>] (hci_rx_task+0x244/0x478 [bluetooth])
>> >> [ 6070.072631] r6:dc647700 r5:00000001 r4:df2ab740
>> >> [ 6070.077362] [<bf003560>] (hci_rx_task+0x0/0x478 [bluetooth]) from
>> >> [<c006b9fc>] (tasklet_action+0x78/0xd8)
>> >> [ 6070.087005] [<c006b984>] (tasklet_action+0x0/0xd8) from [<c006c160>]
>> >>
>> >> Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@nokia.com>
>> >> ---
>> >> net/bluetooth/l2cap.c | 6 ++++++
>> >> 1 files changed, 6 insertions(+), 0 deletions(-)
>> >>
>> >> diff --git a/net/bluetooth/l2cap.c b/net/bluetooth/l2cap.c
>> >> index 400efa2..69b7280 100644
>> >> --- a/net/bluetooth/l2cap.c
>> >> +++ b/net/bluetooth/l2cap.c
>> >> @@ -2830,6 +2830,12 @@ static inline int l2cap_config_rsp(struct
>> >> l2cap_conn *conn, struct l2cap_cmd_hdr
>> >> int len = cmd->len - sizeof(*rsp);
>> >> char req[64];
>> >>
>> >> + if (len > sizeof(req) - sizeof(struct l2cap_conf_req)) {
>> >> + BT_ERR("Config response is too big");
>> >
>> > Remove the BT_ERR, normally we don't print any error on
>> > l2cap_send_disconn_req.
>> >
>> >
>> >> + l2cap_send_disconn_req(conn, sk);
>> >> + goto done;
>> >> + }
>> >> +
>> >> /* throw out any old stored conf requests */
>> >> result = L2CAP_CONF_SUCCESS;
>> >> len = l2cap_parse_conf_rsp(sk, rsp->data,
>> >
>> > Also, this is very rare crash. Even if we add all configure options to
>> > req we won't overwrite it. Doesn't make sense to me send a
>> > configuration option more than once in the same config_{rsp,req}. The
>> > only way to crash l2cap is using a bugous remote stack or a stress test
>> > tools. We need to be protected against those bugous stacks so I'll
>> > ack your patch after you send the updated patch without the BT_ERR.
>> >
>>
>> I am attaching patch to the mail, otherwise it may be screwed up by mailers.
>
> Acked-by: Gustavo F. Padovan <gustavo@padovan.org>
Thanks. I am attaching patch.
Regards,
Andrei
[-- Attachment #2: 0001-Bluetooth-Fix-kernel-crash-on-BT-stress-tests.patch --]
[-- Type: text/x-patch, Size: 2178 bytes --]
From af8cab3087cf4d4865ad88fb25d130ebea108db0 Mon Sep 17 00:00:00 2001
From: Andrei Emeltchenko <andrei.emeltchenko@nokia.com>
Date: Tue, 16 Feb 2010 10:52:33 +0200
Subject: [PATCH] Bluetooth: Fix kernel crash on BT stress tests.
Added very simple check that req buffer has enough space to
fit configuration parameters. Shall be enough to reject packets
with configuration size more than req buffer.
Crash trace below
[ 6069.659393] Unable to handle kernel paging request at virtual address 02000205
[ 6069.673034] Internal error: Oops: 805 [#1] PREEMPT
...
[ 6069.727172] PC is at l2cap_add_conf_opt+0x70/0xf0 [l2cap]
[ 6069.732604] LR is at l2cap_recv_frame+0x1350/0x2e78 [l2cap]
...
[ 6070.030303] Backtrace:
[ 6070.032806] [<bf1c2880>] (l2cap_add_conf_opt+0x0/0xf0 [l2cap]) from
[<bf1c6624>] (l2cap_recv_frame+0x1350/0x2e78 [l2cap])
[ 6070.043823] r8:dc5d3100 r7:df2a91d6 r6:00000001 r5:df2a8000 r4:00000200
[ 6070.050659] [<bf1c52d4>] (l2cap_recv_frame+0x0/0x2e78 [l2cap]) from
[<bf1c8408>] (l2cap_recv_acldata+0x2bc/0x350 [l2cap])
[ 6070.061798] [<bf1c814c>] (l2cap_recv_acldata+0x0/0x350 [l2cap]) from
[<bf0037a4>] (hci_rx_task+0x244/0x478 [bluetooth])
[ 6070.072631] r6:dc647700 r5:00000001 r4:df2ab740
[ 6070.077362] [<bf003560>] (hci_rx_task+0x0/0x478 [bluetooth]) from
[<c006b9fc>] (tasklet_action+0x78/0xd8)
[ 6070.087005] [<c006b984>] (tasklet_action+0x0/0xd8) from [<c006c160>]
Signed-off-by: Andrei Emeltchenko <andrei.emeltchenko@nokia.com>
Acked-by: Gustavo F. Padovan <gustavo@padovan.org>
---
net/bluetooth/l2cap.c | 5 +++++
1 files changed, 5 insertions(+), 0 deletions(-)
diff --git a/net/bluetooth/l2cap.c b/net/bluetooth/l2cap.c
index 930f987..f4258bc 100644
--- a/net/bluetooth/l2cap.c
+++ b/net/bluetooth/l2cap.c
@@ -2897,6 +2897,11 @@ static inline int l2cap_config_rsp(struct l2cap_conn *conn, struct l2cap_cmd_hdr
int len = cmd->len - sizeof(*rsp);
char req[64];
+ if (len > sizeof(req) - sizeof(struct l2cap_conf_req)) {
+ l2cap_send_disconn_req(conn, sk);
+ goto done;
+ }
+
/* throw out any old stored conf requests */
result = L2CAP_CONF_SUCCESS;
len = l2cap_parse_conf_rsp(sk, rsp->data,
--
1.6.0.4
^ permalink raw reply related
* Re: [bluetooth-next V3] Bluetooth: handle device reset event
From: Marcel Holtmann @ 2010-03-19 5:32 UTC (permalink / raw)
To: Tomas Winkler; +Cc: linux-bluetooth, guy.cohen, ron.rindjunsky, Gregory Paskar
In-Reply-To: <1268898246-22693-1-git-send-email-tomas.winkler@intel.com>
Hi Tomas,
> From: Gregory Paskar <gregory.paskar@intel.com>
>
> A Bluetooth device experiencing hardware failure may issue
> a HARDWARE_ERROR hci event. The reaction to this event is device
> reset flow implemented in following sequence.
>
> 1. Notify: HCI_DEV_DOWN
> 2. Reinitialize internal structures.
> 3. Call driver flush function
> 4. Send HCI reset request to the device.
> 5. Send HCI init sequence reset to the device.
> 6. Notify HCI_DEV_UP.
>
> Signed-off-by: Gregory Paskar <gregory.paskar@intel.com>
> Signed-off-by: Tomas Winkler <tomas.winkler@intel.com>
> Reviewed-by: Ron Rindjunsky <ron.rindjunsky@intel.com>
> ---
> V2:
> 1. Fix email typo
> 2. Fix style issues
> V3:
> 1. align with naming convention hw_err_work -> work_hw_err
> 2. use per controller workqueue
>
> include/net/bluetooth/hci.h | 5 ++++
> include/net/bluetooth/hci_core.h | 2 +
> net/bluetooth/hci_core.c | 47 +++++++++++++++++++++++++++++++++++++-
> net/bluetooth/hci_event.c | 3 ++
> 4 files changed, 56 insertions(+), 1 deletions(-)
>
> diff --git a/include/net/bluetooth/hci.h b/include/net/bluetooth/hci.h
> index fc0c502..3f986e7 100644
> --- a/include/net/bluetooth/hci.h
> +++ b/include/net/bluetooth/hci.h
> @@ -695,6 +695,11 @@ struct hci_ev_cmd_status {
> __le16 opcode;
> } __attribute__ ((packed));
>
> +#define HCI_EV_HARDWARE_ERROR 0x10
> +struct hci_ev_hw_error {
> + __u8 hw_code;
> +} __attribute__ ((packed));
> +
So the rule is that the HCI_EV and hci_ev struct names are matching up.
It should be matching what we have in the library (not a hard
requirement though):
#define EVT_HARDWARE_ERROR 0x10
typedef struct {
uint8_t code;
} __attribute__ ((packed)) evt_hardware_error;
So just spell it out hardware_error. This means it is also code and not
hw_code inside the struct.
> #define HCI_EV_ROLE_CHANGE 0x12
> struct hci_ev_role_change {
> __u8 status;
> diff --git a/include/net/bluetooth/hci_core.h b/include/net/bluetooth/hci_core.h
> index e17849e..1c9601d 100644
> --- a/include/net/bluetooth/hci_core.h
> +++ b/include/net/bluetooth/hci_core.h
> @@ -113,6 +113,8 @@ struct hci_dev {
> struct tasklet_struct rx_task;
> struct tasklet_struct tx_task;
>
> + struct work_struct work_hw_err;
> +
I would prefer if you just call it reset_work actually. I know that we
are acting on a hardware error, but the action that we are performing is
actually a full reset. It might be useful for other parts of the stack
as well.
> struct sk_buff_head rx_q;
> struct sk_buff_head raw_q;
> struct sk_buff_head cmd_q;
> diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c
> index 8b4baac..c5a43e3 100644
> --- a/net/bluetooth/hci_core.c
> +++ b/net/bluetooth/hci_core.c
> @@ -839,6 +839,51 @@ static int hci_rfkill_set_block(void *data, bool blocked)
> return 0;
> }
>
> +static void hci_device_hw_error(struct hci_dev *hdev)
> +{
> + hci_req_lock(hdev);
> +
> + /* notify: going down */
> + clear_bit(HCI_UP, &hdev->flags);
> + hci_notify(hdev, HCI_DEV_DOWN);
> +
> + tasklet_disable(&hdev->tx_task);
> + skb_queue_purge(&hdev->rx_q);
> + skb_queue_purge(&hdev->cmd_q);
> +
> + hci_dev_lock_bh(hdev);
> + inquiry_cache_flush(hdev);
> + hci_conn_hash_flush(hdev);
> + hci_dev_unlock_bh(hdev);
> +
> + if (hdev->flush)
> + hdev->flush(hdev);
> +
> + /* reset device */
> + atomic_set(&hdev->cmd_cnt, 1);
> + hdev->acl_cnt = 0;
> + hdev->sco_cnt = 0;
> + hci_reset_req(hdev, 0);
> +
> + /* init device */
> + atomic_set(&hdev->cmd_cnt, 1);
> + hci_init_req(hdev, 0);
> +
> + tasklet_enable(&hdev->tx_task);
> +
> + /* notify: going back up */
> + set_bit(HCI_UP, &hdev->flags);
> + hci_notify(hdev, HCI_DEV_UP);
> +
> + hci_req_unlock(hdev);
> +}
> +
> +static void hci_work_hw_err(struct work_struct *ws)
> +{
> + struct hci_dev *hdev = container_of(ws, struct hci_dev, work_hw_err);
> + hci_device_hw_error(hdev);
> +}
> +
Please name it hci_reset_work to match it properly. And then put
everything in the same function. No need to really split it here.
What I would prefer if we can split out the open/close code and re-use
it it here.
> static const struct rfkill_ops hci_rfkill_ops = {
> .set_block = hci_rfkill_set_block,
> };
> @@ -908,7 +953,7 @@ int hci_register_dev(struct hci_dev *hdev)
> tasklet_init(&hdev->cmd_task, hci_cmd_task,(unsigned long) hdev);
> tasklet_init(&hdev->rx_task, hci_rx_task, (unsigned long) hdev);
> tasklet_init(&hdev->tx_task, hci_tx_task, (unsigned long) hdev);
> -
> + INIT_WORK(&hdev->work_hw_err, hci_work_hw_err);
> skb_queue_head_init(&hdev->rx_q);
> skb_queue_head_init(&hdev->cmd_q);
> skb_queue_head_init(&hdev->raw_q);
I am missing the cancel_work_sync() call in hci_unregister_dev().
> diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c
> index 6c57fc7..6bcf3e9 100644
> --- a/net/bluetooth/hci_event.c
> +++ b/net/bluetooth/hci_event.c
> @@ -1955,6 +1955,9 @@ void hci_event_packet(struct hci_dev *hdev, struct sk_buff *skb)
> case HCI_EV_REMOTE_HOST_FEATURES:
> hci_remote_host_features_evt(hdev, skb);
> break;
> + case HCI_EV_HARDWARE_ERROR:
> + queue_work(hdev->workqueue, &hdev->work_hw_err);
> + break;
>
> default:
> BT_DBG("%s event 0x%x", hdev->name, event);
Since it seems you have the only hardware where this can be re-produced,
it would be great if you include some hcidump -X -V extracts inside the
commit message.
Regards
Marcel
^ permalink raw reply
* BlueZ GSoC 2010
From: Vinicius Gomes @ 2010-03-19 1:50 UTC (permalink / raw)
To: BlueZ
Hi,
BlueZ just got accepted as an organization for this year's Google
Summer of Code.
There is a small list of project ideas here[1], for the next days we
need to polish it and add more content. Any help is appreciated.
We are also looking for mentors, if this idea interests you, please
contact me off-list or go to #bluez-gsoc at freenode, this is also
where most of the discussion regarding GSoC will take place, in case
you just want to follow it.
As always, patches and suggestions are welcome ;-)
And thanks to everyone who contributed ideas to that list.
Cheers,
--
Vinicius Gomes
INdT - Instituto Nokia de Tecnologia
[1] http://hostisdown.org/gsoc/
^ permalink raw reply
* Re: [PATCH 2/2] Add sysfs speed attribute for wacom bluetooth tablet
From: Przemo Firszt @ 2010-03-18 19:12 UTC (permalink / raw)
To: Bastien Nocera; +Cc: linux-bluetooth, marcel, Peter Hutterer, Ping, Jiri Kosina
In-Reply-To: <1268926624.21548.1478.camel@localhost.localdomain>
[-- Attachment #1: Type: text/plain, Size: 1792 bytes --]
Dnia 2010-03-18, czw o godzinie 15:37 +0000, Bastien Nocera pisze:
> On Thu, 2010-03-18 at 15:26 +0000, Przemo Firszt wrote:
>
> > + unsigned char speed;
>
> Could you add some comments as to what values represent what speed?
I changed name from 'speed' to 'high_speed' as per your comment below,
so I think there is no need (unless you think otherwise).
>
> > +static ssize_t wacom_store_speed(struct device *dev,
> > + struct device_attribute *attr,
> > + const char *buf, size_t count)
> > +{
> > + struct hid_device *hdev = container_of(dev, struct hid_device,
> > dev);
> > + int new_speed;
> > +
> > + sscanf(buf, "%1d", &new_speed);
>
> You should check the retval of sscanf as well.
Done, see attached patch.
> > + if (new_speed == 0 || new_speed == 1) {
> > + wacom_poke(hdev, new_speed);
> > + return strnlen(buf, PAGE_SIZE);
> > + } else
> > + return -EINVAL;
> > +}
>
> >
> > +static DEVICE_ATTR(speed, S_IRUGO | S_IWUGO,
> > + wacom_show_speed, wacom_store_speed);
>
> If there's only 2 speeds available, and it's actually a boolean, I'd
> rather you used a name like "high_speed".
>
> Furthermore, wdata->speed doesn't look like it's initialised.
It is initialised by the very first call of wacom_poke from wacom_probe
function. Can you advise if it's enough?
>
> Did you test whether speed switching works after the device has been
> started up?
Yes, it works like a charm, both ways.
[przemo@pldmachine ~]$ echo 0 > /sys/class/hidraw/hidraw1/device/speed
and lag is gone,
[przemo@pldmachine ~]$ echo 1 > /sys/class/hidraw/hidraw1/device/speed
and "rubber band" effect is back.
Thanks for your comments,
Przemo
[-- Attachment #2: 0002-Add-sysfs-speed-attribute-for-wacom-bluetooth-tablet.patch --]
[-- Type: text/x-patch, Size: 2783 bytes --]
>From ec2c13649c3d7188199bfddc06b4211170c28b1c Mon Sep 17 00:00:00 2001
From: Przemo Firszt <przemo@firszt.eu>
Date: Thu, 18 Mar 2010 14:34:34 +0000
Subject: [PATCH 2/2] Add sysfs speed attribute for wacom bluetooth tablet
The attribute allows to change reporting speed of tablet from userspace through
sysfs file. The attribute is RW, valid values: 0 is low speed, 1 is high speed.
High speed is the default setting. Using low speed is a workaround if you
experience lag when using the tablet.
Signed-off-by: Przemo Firszt <przemo@firszt.eu>
---
drivers/hid/hid-wacom.c | 40 +++++++++++++++++++++++++++++++++++++++-
1 files changed, 39 insertions(+), 1 deletions(-)
diff --git a/drivers/hid/hid-wacom.c b/drivers/hid/hid-wacom.c
index f9d4939..97ef626 100644
--- a/drivers/hid/hid-wacom.c
+++ b/drivers/hid/hid-wacom.c
@@ -30,6 +30,7 @@
struct wacom_data {
__u16 tool;
unsigned char butstate;
+ unsigned char high_speed;
#ifdef CONFIG_HID_WACOM_POWER_SUPPLY
int battery_capacity;
struct power_supply battery;
@@ -105,6 +106,7 @@ static int wacom_ac_get_property(struct power_supply *psy,
static void wacom_poke(struct hid_device *hdev, u8 speed)
{
+ struct wacom_data *wdata = hid_get_drvdata(hdev);
int limit, ret;
char rep_data[2];
@@ -128,8 +130,10 @@ static void wacom_poke(struct hid_device *hdev, u8 speed)
HID_FEATURE_REPORT);
} while (ret < 0 && limit-- > 0);
- if (ret >= 0)
+ if (ret >= 0) {
+ wdata->high_speed = speed;
return;
+ }
}
/*
@@ -141,6 +145,35 @@ static void wacom_poke(struct hid_device *hdev, u8 speed)
return;
}
+static ssize_t wacom_show_speed(struct device *dev,
+ struct device_attribute
+ *attr, char *buf)
+{
+ struct wacom_data *wdata = dev_get_drvdata(dev);
+
+ return snprintf(buf, PAGE_SIZE, "%i\n", wdata->high_speed);
+}
+
+static ssize_t wacom_store_speed(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ struct hid_device *hdev = container_of(dev, struct hid_device, dev);
+ int new_speed;
+
+ if (sscanf(buf, "%1d", &new_speed ) != 1)
+ return -EINVAL;
+
+ if (new_speed == 0 || new_speed == 1) {
+ wacom_poke(hdev, new_speed);
+ return strnlen(buf, PAGE_SIZE);
+ } else
+ return -EINVAL;
+}
+
+static DEVICE_ATTR(speed, S_IRUGO | S_IWUGO,
+ wacom_show_speed, wacom_store_speed);
+
static int wacom_raw_event(struct hid_device *hdev, struct hid_report *report,
u8 *raw_data, int size)
{
@@ -297,6 +330,11 @@ static int wacom_probe(struct hid_device *hdev,
goto err_free;
}
+ ret = device_create_file(&hdev->dev, &dev_attr_speed);
+ if (ret)
+ dev_warn(&hdev->dev,
+ "can't create sysfs speed attribute err: %d\n", ret);
+
/* Set Wacom mode 2 with high reporting speed */
wacom_poke(hdev, 1);
--
1.7.0.1
^ permalink raw reply related
* Re: [PATCH 1/2] Add separate mode switching function wacom bluetooth pen tablet.
From: Bastien Nocera @ 2010-03-18 15:39 UTC (permalink / raw)
To: Przemo Firszt; +Cc: linux-bluetooth, marcel, Ping, Peter Hutterer, Jiri Kosina
In-Reply-To: <1268925902.12672.25.camel@pldmachine>
On Thu, 2010-03-18 at 15:25 +0000, Przemo Firszt wrote:
> Hi,
> Two patches to allow switching of reporting speed of wacom bluetooth
> tablet from userspace through sysfs.
Signed-off-by: Bastien Nocera <hadess@hadess.net>
Cheers
^ permalink raw reply
* Re: [PATCH 2/2] Add sysfs speed attribute for wacom bluetooth tablet
From: Bastien Nocera @ 2010-03-18 15:37 UTC (permalink / raw)
To: Przemo Firszt; +Cc: linux-bluetooth, marcel, Peter Hutterer, Ping, Jiri Kosina
In-Reply-To: <1268926015.12672.27.camel@pldmachine>
On Thu, 2010-03-18 at 15:26 +0000, Przemo Firszt wrote:
> + unsigned char speed;
Could you add some comments as to what values represent what speed?
> +static ssize_t wacom_store_speed(struct device *dev,
> + struct device_attribute *attr,
> + const char *buf, size_t count)
> +{
> + struct hid_device *hdev = container_of(dev, struct hid_device,
> dev);
> + int new_speed;
> +
> + sscanf(buf, "%1d", &new_speed);
You should check the retval of sscanf as well.
> + if (new_speed == 0 || new_speed == 1) {
> + wacom_poke(hdev, new_speed);
> + return strnlen(buf, PAGE_SIZE);
> + } else
> + return -EINVAL;
> +}
>
> +static DEVICE_ATTR(speed, S_IRUGO | S_IWUGO,
> + wacom_show_speed, wacom_store_speed);
If there's only 2 speeds available, and it's actually a boolean, I'd
rather you used a name like "high_speed".
Furthermore, wdata->speed doesn't look like it's initialised.
Did you test whether speed switching works after the device has been
started up?
Cheers
^ permalink raw reply
* [PATCH 2/2] Add sysfs speed attribute for wacom bluetooth tablet
From: Przemo Firszt @ 2010-03-18 15:26 UTC (permalink / raw)
To: linux-bluetooth, Bastien Nocera, marcel, Peter Hutterer, Ping,
Jiri Kosina
In-Reply-To: <1268925902.12672.25.camel@pldmachine>
[-- Attachment #1: Type: text/plain, Size: 21 bytes --]
Patch 2/2
--
Przemo
[-- Attachment #2: 0002-Add-sysfs-speed-attribute-for-wacom-bluetooth-tablet.patch --]
[-- Type: text/x-patch, Size: 2735 bytes --]
>From 92b0a06c748ea0a853c369595444dd411b32f314 Mon Sep 17 00:00:00 2001
From: Przemo Firszt <przemo@firszt.eu>
Date: Thu, 18 Mar 2010 14:34:34 +0000
Subject: [PATCH 2/2] Add sysfs speed attribute for wacom bluetooth tablet
The attribute allows to change reporting speed of tablet from userspace through
sysfs file. The attribute is RW, valid values: 0 is low speed, 1 is high speed.
High speed is the default setting. Using low speed is a workaround if you
experience lag when using the tablet.
Signed-off-by: Przemo Firszt <przemo@firszt.eu>
---
drivers/hid/hid-wacom.c | 38 +++++++++++++++++++++++++++++++++++++-
1 files changed, 37 insertions(+), 1 deletions(-)
diff --git a/drivers/hid/hid-wacom.c b/drivers/hid/hid-wacom.c
index f9d4939..34d96e0 100644
--- a/drivers/hid/hid-wacom.c
+++ b/drivers/hid/hid-wacom.c
@@ -30,6 +30,7 @@
struct wacom_data {
__u16 tool;
unsigned char butstate;
+ unsigned char speed;
#ifdef CONFIG_HID_WACOM_POWER_SUPPLY
int battery_capacity;
struct power_supply battery;
@@ -105,6 +106,7 @@ static int wacom_ac_get_property(struct power_supply *psy,
static void wacom_poke(struct hid_device *hdev, u8 speed)
{
+ struct wacom_data *wdata = hid_get_drvdata(hdev);
int limit, ret;
char rep_data[2];
@@ -128,8 +130,10 @@ static void wacom_poke(struct hid_device *hdev, u8 speed)
HID_FEATURE_REPORT);
} while (ret < 0 && limit-- > 0);
- if (ret >= 0)
+ if (ret >= 0) {
+ wdata->speed = speed;
return;
+ }
}
/*
@@ -141,6 +145,33 @@ static void wacom_poke(struct hid_device *hdev, u8 speed)
return;
}
+static ssize_t wacom_show_speed(struct device *dev,
+ struct device_attribute
+ *attr, char *buf)
+{
+ struct wacom_data *wdata = dev_get_drvdata(dev);
+
+ return snprintf(buf, PAGE_SIZE, "%i\n", wdata->speed);
+}
+
+static ssize_t wacom_store_speed(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ struct hid_device *hdev = container_of(dev, struct hid_device, dev);
+ int new_speed;
+
+ sscanf(buf, "%1d", &new_speed);
+ if (new_speed == 0 || new_speed == 1) {
+ wacom_poke(hdev, new_speed);
+ return strnlen(buf, PAGE_SIZE);
+ } else
+ return -EINVAL;
+}
+
+static DEVICE_ATTR(speed, S_IRUGO | S_IWUGO,
+ wacom_show_speed, wacom_store_speed);
+
static int wacom_raw_event(struct hid_device *hdev, struct hid_report *report,
u8 *raw_data, int size)
{
@@ -297,6 +328,11 @@ static int wacom_probe(struct hid_device *hdev,
goto err_free;
}
+ ret = device_create_file(&hdev->dev, &dev_attr_speed);
+ if (ret)
+ dev_warn(&hdev->dev,
+ "can't create sysfs speed attribute err: %d\n", ret);
+
/* Set Wacom mode 2 with high reporting speed */
wacom_poke(hdev, 1);
--
1.7.0.1
^ permalink raw reply related
* [PATCH 1/2] Add separate mode switching function wacom bluetooth pen tablet.
From: Przemo Firszt @ 2010-03-18 15:25 UTC (permalink / raw)
To: linux-bluetooth, Bastien Nocera, marcel, Ping, Peter Hutterer,
Jiri Kosina
[-- Attachment #1: Type: text/plain, Size: 133 bytes --]
Hi,
Two patches to allow switching of reporting speed of wacom bluetooth
tablet from userspace through sysfs.
kind reagrds,
Przemo
[-- Attachment #2: 0001-Add-separate-mode-switching-function-wacom-bluetooth.patch --]
[-- Type: text/x-patch, Size: 2996 bytes --]
>From ac9a87b92cf2f8cc27a1d29123c5fa1a8bebd71a Mon Sep 17 00:00:00 2001
From: Przemo Firszt <przemo@firszt.eu>
Date: Thu, 18 Mar 2010 11:58:22 +0000
Subject: [PATCH 1/2] Add separate mode switching function wacom bluetooth pen tablet.
wacom_poke function allows to switch tablet reporting speed. The patch
dosen't add any new functionality, but it's preparation for user-space
speed switching through sysfs.
Signed-off-by: Przemo Firszt <przemo@firszt.eu>
---
drivers/hid/hid-wacom.c | 66 ++++++++++++++++++++++++++++------------------
1 files changed, 40 insertions(+), 26 deletions(-)
diff --git a/drivers/hid/hid-wacom.c b/drivers/hid/hid-wacom.c
index 4d2d2a2..f9d4939 100644
--- a/drivers/hid/hid-wacom.c
+++ b/drivers/hid/hid-wacom.c
@@ -103,6 +103,44 @@ static int wacom_ac_get_property(struct power_supply *psy,
}
#endif
+static void wacom_poke(struct hid_device *hdev, u8 speed)
+{
+ int limit, ret;
+ char rep_data[2];
+
+ rep_data[0] = 0x03 ; rep_data[1] = 0x00;
+ limit = 3;
+ do {
+ ret = hdev->hid_output_raw_report(hdev, rep_data, 2,
+ HID_FEATURE_REPORT);
+ } while (ret < 0 && limit-- > 0);
+
+ if (ret >= 0) {
+ if (speed == 0)
+ rep_data[0] = 0x05;
+ else
+ rep_data[0] = 0x06;
+
+ rep_data[1] = 0x00;
+ limit = 3;
+ do {
+ ret = hdev->hid_output_raw_report(hdev, rep_data, 2,
+ HID_FEATURE_REPORT);
+ } while (ret < 0 && limit-- > 0);
+
+ if (ret >= 0)
+ return;
+ }
+
+ /*
+ * Note that if the raw queries fail, it's not a hard failure and it
+ * is safe to continue
+ */
+ dev_warn(&hdev->dev, "failed to poke device, command %d, err %d\n",
+ rep_data[0], ret);
+ return;
+}
+
static int wacom_raw_event(struct hid_device *hdev, struct hid_report *report,
u8 *raw_data, int size)
{
@@ -236,9 +274,7 @@ static int wacom_probe(struct hid_device *hdev,
struct hid_input *hidinput;
struct input_dev *input;
struct wacom_data *wdata;
- char rep_data[2];
int ret;
- int limit;
wdata = kzalloc(sizeof(*wdata), GFP_KERNEL);
if (wdata == NULL) {
@@ -261,30 +297,8 @@ static int wacom_probe(struct hid_device *hdev,
goto err_free;
}
- /*
- * Note that if the raw queries fail, it's not a hard failure and it
- * is safe to continue
- */
-
- /* Set Wacom mode2 */
- rep_data[0] = 0x03; rep_data[1] = 0x00;
- limit = 3;
- do {
- ret = hdev->hid_output_raw_report(hdev, rep_data, 2,
- HID_FEATURE_REPORT);
- } while (ret < 0 && limit-- > 0);
- if (ret < 0)
- dev_warn(&hdev->dev, "failed to poke device #1, %d\n", ret);
-
- /* 0x06 - high reporting speed, 0x05 - low speed */
- rep_data[0] = 0x06; rep_data[1] = 0x00;
- limit = 3;
- do {
- ret = hdev->hid_output_raw_report(hdev, rep_data, 2,
- HID_FEATURE_REPORT);
- } while (ret < 0 && limit-- > 0);
- if (ret < 0)
- dev_warn(&hdev->dev, "failed to poke device #2, %d\n", ret);
+ /* Set Wacom mode 2 with high reporting speed */
+ wacom_poke(hdev, 1);
#ifdef CONFIG_HID_WACOM_POWER_SUPPLY
wdata->battery.properties = wacom_battery_props;
--
1.7.0.1
^ permalink raw reply related
* [bluetooth-next V3] Bluetooth: handle device reset event
From: Tomas Winkler @ 2010-03-18 7:44 UTC (permalink / raw)
To: marcel, linux-bluetooth
Cc: guy.cohen, ron.rindjunsky, Gregory Paskar, Tomas Winkler
From: Gregory Paskar <gregory.paskar@intel.com>
A Bluetooth device experiencing hardware failure may issue
a HARDWARE_ERROR hci event. The reaction to this event is device
reset flow implemented in following sequence.
1. Notify: HCI_DEV_DOWN
2. Reinitialize internal structures.
3. Call driver flush function
4. Send HCI reset request to the device.
5. Send HCI init sequence reset to the device.
6. Notify HCI_DEV_UP.
Signed-off-by: Gregory Paskar <gregory.paskar@intel.com>
Signed-off-by: Tomas Winkler <tomas.winkler@intel.com>
Reviewed-by: Ron Rindjunsky <ron.rindjunsky@intel.com>
---
V2:
1. Fix email typo
2. Fix style issues
V3:
1. align with naming convention hw_err_work -> work_hw_err
2. use per controller workqueue
include/net/bluetooth/hci.h | 5 ++++
include/net/bluetooth/hci_core.h | 2 +
net/bluetooth/hci_core.c | 47 +++++++++++++++++++++++++++++++++++++-
net/bluetooth/hci_event.c | 3 ++
4 files changed, 56 insertions(+), 1 deletions(-)
diff --git a/include/net/bluetooth/hci.h b/include/net/bluetooth/hci.h
index fc0c502..3f986e7 100644
--- a/include/net/bluetooth/hci.h
+++ b/include/net/bluetooth/hci.h
@@ -695,6 +695,11 @@ struct hci_ev_cmd_status {
__le16 opcode;
} __attribute__ ((packed));
+#define HCI_EV_HARDWARE_ERROR 0x10
+struct hci_ev_hw_error {
+ __u8 hw_code;
+} __attribute__ ((packed));
+
#define HCI_EV_ROLE_CHANGE 0x12
struct hci_ev_role_change {
__u8 status;
diff --git a/include/net/bluetooth/hci_core.h b/include/net/bluetooth/hci_core.h
index e17849e..1c9601d 100644
--- a/include/net/bluetooth/hci_core.h
+++ b/include/net/bluetooth/hci_core.h
@@ -113,6 +113,8 @@ struct hci_dev {
struct tasklet_struct rx_task;
struct tasklet_struct tx_task;
+ struct work_struct work_hw_err;
+
struct sk_buff_head rx_q;
struct sk_buff_head raw_q;
struct sk_buff_head cmd_q;
diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c
index 8b4baac..c5a43e3 100644
--- a/net/bluetooth/hci_core.c
+++ b/net/bluetooth/hci_core.c
@@ -839,6 +839,51 @@ static int hci_rfkill_set_block(void *data, bool blocked)
return 0;
}
+static void hci_device_hw_error(struct hci_dev *hdev)
+{
+ hci_req_lock(hdev);
+
+ /* notify: going down */
+ clear_bit(HCI_UP, &hdev->flags);
+ hci_notify(hdev, HCI_DEV_DOWN);
+
+ tasklet_disable(&hdev->tx_task);
+ skb_queue_purge(&hdev->rx_q);
+ skb_queue_purge(&hdev->cmd_q);
+
+ hci_dev_lock_bh(hdev);
+ inquiry_cache_flush(hdev);
+ hci_conn_hash_flush(hdev);
+ hci_dev_unlock_bh(hdev);
+
+ if (hdev->flush)
+ hdev->flush(hdev);
+
+ /* reset device */
+ atomic_set(&hdev->cmd_cnt, 1);
+ hdev->acl_cnt = 0;
+ hdev->sco_cnt = 0;
+ hci_reset_req(hdev, 0);
+
+ /* init device */
+ atomic_set(&hdev->cmd_cnt, 1);
+ hci_init_req(hdev, 0);
+
+ tasklet_enable(&hdev->tx_task);
+
+ /* notify: going back up */
+ set_bit(HCI_UP, &hdev->flags);
+ hci_notify(hdev, HCI_DEV_UP);
+
+ hci_req_unlock(hdev);
+}
+
+static void hci_work_hw_err(struct work_struct *ws)
+{
+ struct hci_dev *hdev = container_of(ws, struct hci_dev, work_hw_err);
+ hci_device_hw_error(hdev);
+}
+
static const struct rfkill_ops hci_rfkill_ops = {
.set_block = hci_rfkill_set_block,
};
@@ -908,7 +953,7 @@ int hci_register_dev(struct hci_dev *hdev)
tasklet_init(&hdev->cmd_task, hci_cmd_task,(unsigned long) hdev);
tasklet_init(&hdev->rx_task, hci_rx_task, (unsigned long) hdev);
tasklet_init(&hdev->tx_task, hci_tx_task, (unsigned long) hdev);
-
+ INIT_WORK(&hdev->work_hw_err, hci_work_hw_err);
skb_queue_head_init(&hdev->rx_q);
skb_queue_head_init(&hdev->cmd_q);
skb_queue_head_init(&hdev->raw_q);
diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c
index 6c57fc7..6bcf3e9 100644
--- a/net/bluetooth/hci_event.c
+++ b/net/bluetooth/hci_event.c
@@ -1955,6 +1955,9 @@ void hci_event_packet(struct hci_dev *hdev, struct sk_buff *skb)
case HCI_EV_REMOTE_HOST_FEATURES:
hci_remote_host_features_evt(hdev, skb);
break;
+ case HCI_EV_HARDWARE_ERROR:
+ queue_work(hdev->workqueue, &hdev->work_hw_err);
+ break;
default:
BT_DBG("%s event 0x%x", hdev->name, event);
--
1.6.6.1
---------------------------------------------------------------------
Intel Israel (74) Limited
This e-mail and any attachments may contain confidential material for
the sole use of the intended recipient(s). Any review or distribution
by others is strictly prohibited. If you are not the intended
recipient, please contact the sender and delete all copies.
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox