jswap.c
/*
jswap 0.1 -- swap joystick buttons or axes
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301, USA.
*/
#include <sys/ioctl.h>
#include <sys/types.h>
#include <stdlib.h>
#include <fcntl.h>
#include <stdio.h>
#include <string.h>
#include <linux/joystick.h>
char *device;
unsigned char num_axes = 2;
unsigned char num_buttons = 4;
int version = 0x000800;
char model[128] = "Unknown";
__u16 buttons[KEY_MAX - BTN_MISC + 1];
__u8 axes[ABS_MAX + 1];
void usage(void) {
puts("Usage: jswap [<spec>,...] device");
puts(" <spec> = [a|b]:<idx>,<idx>");
}
void print_info(void) {
int i;
printf("%s: %d axes, %d buttons (\"%s\")\n",
device, num_axes, num_buttons, model);
printf("buttonmap : [");
for(i=0; i<num_buttons; i++) {
if(i == 0)
printf("%d", buttons[i]);
else
printf(", %d", buttons[i]);
}
printf("]\n");
printf("axismap : [");
for(i=0; i<num_axes; i++) {
if(i == 0)
printf("%d", axes[i]);
else
printf(", %d", axes[i]);
}
printf("]\n");
}
int check_value(int val, int max, char *type, char *type_pl) {
if(val > max || val < 0) {
printf("jswap: %d: no such %s. (%s: %d %s (0-%d))\n",
val, type, device, max+1, type_pl, max);
return 1;
}
return 0;
}
int swap_axis(int a, int b) {
int tmp = axes[a];
axes[a] = axes[b];
axes[b] = tmp;
return 0;
}
int swap_button(int a, int b) {
int tmp = buttons[a];
buttons[a] = buttons[b];
buttons[b] = tmp;
return 0;
}
int main(int argc, char **argv) {
int fd;
if (argc == 1) {
usage();
exit(1);
}
device = argv[argc - 1];
if ((fd = open(device, O_RDONLY)) < 0) {
char *fmt = "jswap: can't open joystick device '%s'";
char msg[strlen(fmt)+strlen(device)];
sprintf(msg, fmt, device);
perror(msg);
exit(1);
}
if(ioctl(fd, JSIOCGVERSION, &version)) {
perror("jswap: error getting driver version");
exit(1);
}
if(ioctl(fd, JSIOCGAXES, &num_axes)) {
perror("jswap: error getting number of axes");
exit(1);
}
if(ioctl(fd, JSIOCGBUTTONS, &num_buttons)) {
perror("jswap: error getting number of axes");
exit(1);
}
if(ioctl(fd, JSIOCGNAME(128), model) < 0) {
perror("jswap: error getting joystick name");
exit(1);
}
if(ioctl(fd, JSIOCGAXMAP, axes)) {
perror("jswap: error getting axis map");
exit(1);
}
if(ioctl(fd, JSIOCGBTNMAP, buttons)) {
perror("jswap: error getting button map");
exit(1);
}
if(argc == 2) {
print_info();
}
if(argc > 2) {
int i;
char *swap;
int a = -1;
int b = -1;
for( i=1; i<argc-1; i++) {
swap = argv[i];
sscanf(swap+2, "%d,", &a);
sscanf(index(swap, ','), ",%d", &b);
if(a == -1 || b == -1) {
usage();
exit(1);
}
if(strstr(swap, "a:") != NULL) {
if( (check_value(a, num_axes-1, "axis", "axes") |
check_value(b, num_axes-1, "axis", "axes")) == 0) {
swap_axis(a, b);
}
else {
exit(1);
}
}
if(strstr(swap, "b:") != NULL) {
if( (check_value(a, num_buttons-1, "button", "buttons") |
check_value(b, num_buttons-1, "button", "buttons")) == 0) {
swap_button(a, b);
}
else {
exit(1);
}
}
}
}
if(ioctl(fd, JSIOCSAXMAP, axes)) {
perror("jswap: error setting button map");
exit(1);
}
if(ioctl(fd, JSIOCSBTNMAP, buttons)) {
perror("jswap: error setting button map");
exit(1);
}
close(fd);
return 0;
}
Here's how to compile and use it to swap axes 0 and 1:
$ gcc -I/usr/src/linux-$(uname -r)/include -o jswap jswap.c
$./jswap
Usage: jswap [<spec>,...] device
<spec> = [a|b]:<idx>,<idx>
$ ./jswap /dev/js0
/dev/js0: 2 axes, 4 buttons ("MOSIC SPEED-LINK Competition Pro ")
buttonmap : [305, 304, 306, 307]
axismap : [0, 1]
$ ./jswap a:0,1 /dev/js0
$ ./jswap /dev/js0
/dev/js0: 2 axes, 4 buttons ("MOSIC SPEED-LINK Competition Pro ")
buttonmap : [305, 304, 306, 307]
axismap : [1, 0]
to swap axes, you'd use: jswap a:0,1 /dev/js0
to swap buttons one and two: jswap b:0,1 /dev/js0
to swap buttons three and four: jswap b:2,3
So the values given are indices into the arrays shown by jswap /dev/js0 (indices start with 0)
Hope this helps!
]]>Sorry for my bad english
Thanks
]]>