diff options
Diffstat (limited to 'drivers/input/joystick/spaceorb.c')
-rw-r--r-- | drivers/input/joystick/spaceorb.c | 78 |
1 files changed, 36 insertions, 42 deletions
diff --git a/drivers/input/joystick/spaceorb.c b/drivers/input/joystick/spaceorb.c index 01fd2e4791ae..7c123a01c58e 100644 --- a/drivers/input/joystick/spaceorb.c +++ b/drivers/input/joystick/spaceorb.c | |||
@@ -52,15 +52,13 @@ MODULE_LICENSE("GPL"); | |||
52 | 52 | ||
53 | static int spaceorb_buttons[] = { BTN_TL, BTN_TR, BTN_Y, BTN_X, BTN_B, BTN_A }; | 53 | static int spaceorb_buttons[] = { BTN_TL, BTN_TR, BTN_Y, BTN_X, BTN_B, BTN_A }; |
54 | static int spaceorb_axes[] = { ABS_X, ABS_Y, ABS_Z, ABS_RX, ABS_RY, ABS_RZ }; | 54 | static int spaceorb_axes[] = { ABS_X, ABS_Y, ABS_Z, ABS_RX, ABS_RY, ABS_RZ }; |
55 | static char *spaceorb_name = "SpaceTec SpaceOrb 360 / Avenger"; | ||
56 | 55 | ||
57 | /* | 56 | /* |
58 | * Per-Orb data. | 57 | * Per-Orb data. |
59 | */ | 58 | */ |
60 | 59 | ||
61 | struct spaceorb { | 60 | struct spaceorb { |
62 | struct input_dev dev; | 61 | struct input_dev *dev; |
63 | struct serio *serio; | ||
64 | int idx; | 62 | int idx; |
65 | unsigned char data[SPACEORB_MAX_LENGTH]; | 63 | unsigned char data[SPACEORB_MAX_LENGTH]; |
66 | char phys[32]; | 64 | char phys[32]; |
@@ -78,7 +76,7 @@ static unsigned char *spaceorb_errors[] = { "EEPROM storing 0 failed", "Receive | |||
78 | 76 | ||
79 | static void spaceorb_process_packet(struct spaceorb *spaceorb, struct pt_regs *regs) | 77 | static void spaceorb_process_packet(struct spaceorb *spaceorb, struct pt_regs *regs) |
80 | { | 78 | { |
81 | struct input_dev *dev = &spaceorb->dev; | 79 | struct input_dev *dev = spaceorb->dev; |
82 | unsigned char *data = spaceorb->data; | 80 | unsigned char *data = spaceorb->data; |
83 | unsigned char c = 0; | 81 | unsigned char c = 0; |
84 | int axes[6]; | 82 | int axes[6]; |
@@ -95,8 +93,8 @@ static void spaceorb_process_packet(struct spaceorb *spaceorb, struct pt_regs *r | |||
95 | case 'R': /* Reset packet */ | 93 | case 'R': /* Reset packet */ |
96 | spaceorb->data[spaceorb->idx - 1] = 0; | 94 | spaceorb->data[spaceorb->idx - 1] = 0; |
97 | for (i = 1; i < spaceorb->idx && spaceorb->data[i] == ' '; i++); | 95 | for (i = 1; i < spaceorb->idx && spaceorb->data[i] == ' '; i++); |
98 | printk(KERN_INFO "input: %s [%s] on %s\n", | 96 | printk(KERN_INFO "input: %s [%s] is %s\n", |
99 | spaceorb_name, spaceorb->data + i, spaceorb->serio->phys); | 97 | dev->name, spaceorb->data + i, spaceorb->phys); |
100 | break; | 98 | break; |
101 | 99 | ||
102 | case 'D': /* Ball + button data */ | 100 | case 'D': /* Ball + button data */ |
@@ -123,7 +121,7 @@ static void spaceorb_process_packet(struct spaceorb *spaceorb, struct pt_regs *r | |||
123 | 121 | ||
124 | case 'E': /* Error packet */ | 122 | case 'E': /* Error packet */ |
125 | if (spaceorb->idx != 4) return; | 123 | if (spaceorb->idx != 4) return; |
126 | printk(KERN_ERR "joy-spaceorb: Device error. [ "); | 124 | printk(KERN_ERR "spaceorb: Device error. [ "); |
127 | for (i = 0; i < 7; i++) if (data[1] & (1 << i)) printk("%s ", spaceorb_errors[i]); | 125 | for (i = 0; i < 7; i++) if (data[1] & (1 << i)) printk("%s ", spaceorb_errors[i]); |
128 | printk("]\n"); | 126 | printk("]\n"); |
129 | break; | 127 | break; |
@@ -154,9 +152,9 @@ static void spaceorb_disconnect(struct serio *serio) | |||
154 | { | 152 | { |
155 | struct spaceorb* spaceorb = serio_get_drvdata(serio); | 153 | struct spaceorb* spaceorb = serio_get_drvdata(serio); |
156 | 154 | ||
157 | input_unregister_device(&spaceorb->dev); | ||
158 | serio_close(serio); | 155 | serio_close(serio); |
159 | serio_set_drvdata(serio, NULL); | 156 | serio_set_drvdata(serio, NULL); |
157 | input_unregister_device(spaceorb->dev); | ||
160 | kfree(spaceorb); | 158 | kfree(spaceorb); |
161 | } | 159 | } |
162 | 160 | ||
@@ -169,52 +167,48 @@ static void spaceorb_disconnect(struct serio *serio) | |||
169 | static int spaceorb_connect(struct serio *serio, struct serio_driver *drv) | 167 | static int spaceorb_connect(struct serio *serio, struct serio_driver *drv) |
170 | { | 168 | { |
171 | struct spaceorb *spaceorb; | 169 | struct spaceorb *spaceorb; |
172 | int i, t; | 170 | struct input_dev *input_dev; |
173 | int err; | 171 | int err = -ENOMEM; |
174 | 172 | int i; | |
175 | if (!(spaceorb = kmalloc(sizeof(struct spaceorb), GFP_KERNEL))) | ||
176 | return -ENOMEM; | ||
177 | |||
178 | memset(spaceorb, 0, sizeof(struct spaceorb)); | ||
179 | 173 | ||
180 | spaceorb->dev.evbit[0] = BIT(EV_KEY) | BIT(EV_ABS); | 174 | spaceorb = kzalloc(sizeof(struct spaceorb), GFP_KERNEL); |
175 | input_dev = input_allocate_device(); | ||
176 | if (!spaceorb || !input_dev) | ||
177 | goto fail; | ||
181 | 178 | ||
182 | for (i = 0; i < 6; i++) | 179 | spaceorb->dev = input_dev; |
183 | set_bit(spaceorb_buttons[i], spaceorb->dev.keybit); | 180 | sprintf(spaceorb->phys, "%s/input0", serio->phys); |
184 | 181 | ||
185 | for (i = 0; i < 6; i++) { | 182 | input_dev->name = "SpaceTec SpaceOrb 360 / Avenger"; |
186 | t = spaceorb_axes[i]; | 183 | input_dev->phys = spaceorb->phys; |
187 | set_bit(t, spaceorb->dev.absbit); | 184 | input_dev->id.bustype = BUS_RS232; |
188 | spaceorb->dev.absmin[t] = -508; | 185 | input_dev->id.vendor = SERIO_SPACEORB; |
189 | spaceorb->dev.absmax[t] = 508; | 186 | input_dev->id.product = 0x0001; |
190 | } | 187 | input_dev->id.version = 0x0100; |
188 | input_dev->cdev.dev = &serio->dev; | ||
189 | input_dev->private = spaceorb; | ||
191 | 190 | ||
192 | spaceorb->serio = serio; | 191 | input_dev->evbit[0] = BIT(EV_KEY) | BIT(EV_ABS); |
193 | spaceorb->dev.private = spaceorb; | ||
194 | 192 | ||
195 | sprintf(spaceorb->phys, "%s/input0", serio->phys); | 193 | for (i = 0; i < 6; i++) |
194 | set_bit(spaceorb_buttons[i], input_dev->keybit); | ||
196 | 195 | ||
197 | init_input_dev(&spaceorb->dev); | 196 | for (i = 0; i < 6; i++) |
198 | spaceorb->dev.name = spaceorb_name; | 197 | input_set_abs_params(input_dev, spaceorb_axes[i], -508, 508, 0, 0); |
199 | spaceorb->dev.phys = spaceorb->phys; | ||
200 | spaceorb->dev.id.bustype = BUS_RS232; | ||
201 | spaceorb->dev.id.vendor = SERIO_SPACEORB; | ||
202 | spaceorb->dev.id.product = 0x0001; | ||
203 | spaceorb->dev.id.version = 0x0100; | ||
204 | spaceorb->dev.dev = &serio->dev; | ||
205 | 198 | ||
206 | serio_set_drvdata(serio, spaceorb); | 199 | serio_set_drvdata(serio, spaceorb); |
207 | 200 | ||
208 | err = serio_open(serio, drv); | 201 | err = serio_open(serio, drv); |
209 | if (err) { | 202 | if (err) |
210 | serio_set_drvdata(serio, NULL); | 203 | goto fail; |
211 | kfree(spaceorb); | ||
212 | return err; | ||
213 | } | ||
214 | |||
215 | input_register_device(&spaceorb->dev); | ||
216 | 204 | ||
205 | input_register_device(spaceorb->dev); | ||
217 | return 0; | 206 | return 0; |
207 | |||
208 | fail: serio_set_drvdata(serio, NULL); | ||
209 | input_free_device(input_dev); | ||
210 | kfree(spaceorb); | ||
211 | return err; | ||
218 | } | 212 | } |
219 | 213 | ||
220 | /* | 214 | /* |