📄 can_ioctl.h
字号:
#include <linux/ioctl.h>
int afm,lom,stm,sm,mode,err_count,arb_count;
struct err_cap_struct *err_capture;
struct arb_cap_struct *arb_capture;
unsigned long flag;
int irq,level;
enum bau baud;
static int send_delay=200;
static int noblock_delay=100;
static int delay_by_baud=2;
int status;
struct filter_struct *filter;
extern int modify_irq(int , struct CAN_device_struct *);
extern void set_baudrate(enum bau,int);
extern void can_reset_buf();
#define CAN_IOC_MAGIC 'k'
#define CAN_IOCRESET _IO(CAN_IOC_MAGIC, 0)
#define CAN_SET_NOBLOCKDELAY _IOW(CAN_IOC_MAGIC,1,int)
#define CAN_SET_TRIGLEVEL _IOW(CAN_IOC_MAGIC,2,int)
#define CAN_SET_BAUDRATE _IOW(CAN_IOC_MAGIC,3,enum bau)
#define CAN_SET_AFM _IOW(CAN_IOC_MAGIC,4,int)
#define CAN_SET_LOM _IOW(CAN_IOC_MAGIC,5,int)
#define CAN_SET_SM _IOW(CAN_IOC_MAGIC,6,int)
#define CAN_SET_STM _IOW(CAN_IOC_MAGIC,7,int)
#define CAN_SET_FILTER _IOW(CAN_IOC_MAGIC,8,filter)
#define CAN_SET_FILTER1 _IOW(CAN_IOC_MAGIC,9,filter)
#define CAN_SET_FILTER2 _IOW(CAN_IOC_MAGIC,10,filter)
#define CAN_GET_STATUS _IOR(CAN_IOC_MAGIC,11,int)
#define CAN_GET_MODE _IOR(CAN_IOC_MAGIC,12,int)
#define CAN_GET_FILTER _IOR(CAN_IOC_MAGIC,13,filter)
#define CAN_GET_ERRCOUNT _IOR(CAN_IOC_MAGIC,14,int)
#define CAN_GET_ERRCAPTURE _IOR(CAN_IOC_MAGIC,15,err_capture)
#define CAN_GET_BAUDRATE _IOR(CAN_IOC_MAGIC,16,enum bau )
#define CAN_GET_ARBCOUNT _IOR(CAN_IOC_MAGIC,17,int)
#define CAN_GET_ARBCAPTURE _IOR(CAN_IOC_MAGIC,18,arb_capture)
#define CAN_RESET _IO(CAN_IOC_MAGIC, 19) /* debugging tool */
#define CAN_SET_DELAY _IOW(CAN_IOC_MAGIC,20,int)
#define CAN_SET_IRQ _IOW(CAN_IOC_MAGIC,21,int)
#define CAN_IOC_MAXNR 22
int enable_set(struct CAN_device_struct *dev)
{
int loop=0;
while ((test_bit(0,&dev->rx_lock))||
(test_bit(0,&dev->tx_lock))) {
//____udelay(100000);
if (loop++>3) {
printk("the device is busy ,don't change the parms\n");
return -1;
}
}
return 0;
}
int CAN_ioctl(struct inode *inode, struct file *filp,
unsigned int cmd, unsigned long arg)
{
int err = 1, size = _IOC_SIZE(cmd); /* the size bitfield in cmd */
unsigned long flag;
struct CAN_device_struct *dev=filp->private_data;
if (_IOC_TYPE(cmd) != CAN_IOC_MAGIC) {
printk("cmd type is not invalid\n");
return -EINVAL;
}
if (_IOC_NR(cmd) > CAN_IOC_MAXNR) {
printk("cmd is not over max numbe\n");
return -EINVAL;
}
if (_IOC_DIR(cmd) & _IOC_READ)
err = access_ok(VERIFY_WRITE, (void *)arg, size);
else if (_IOC_DIR(cmd) & _IOC_WRITE)
err = access_ok(VERIFY_READ, (void *)arg, size);
if (!err) {
printk("addrss is not valid\n");
return err;
}
switch(cmd) {
case CAN_IOCRESET:
printk("enter iocreset\n");
can_ioc_reset(dev);
printk("ioc rx=%d,tx=%d\n",dev->rx_lock,dev->tx_lock);
dev->recv_head=dev->recv_tail=0;
memset(dev->recv_data,0,4096);
//memset_io(dev->base_addr+0x100,0,51*13);
//memset_io(dev->base_addr+0x400,0,51*13);
clear_bit(0,&dev->rx_lock);
clear_bit(0,&dev->tx_lock);
break;
case CAN_SET_IRQ:
printk("begin can_set_irq\n");
if (get_user(irq,(unsigned short int *)arg))
return -EFAULT;
if (enable_set(dev))
return -1;
save_flags(flag);
cli();
if (modify_irq(irq,dev)) {
restore_flags(flag);
printk("modify irq failed\n");
return -1;
}
restore_flags(flag);
break;
case CAN_SET_TRIGLEVEL:
printk("begin can_set_triglevel\n");
if (get_user(level,(int *)arg))
return -EFAULT;
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
set_trig_level(level,dev->base_addr);
dev->parm->trig_level=level ? level : 1;
restore_flags(flag);
break;
case CAN_SET_DELAY:
printk("begin set send delay \n");
if (enable_set(dev))
return -1;
if (get_user(send_delay,(int *)arg))
return -EFAULT;
break;
case CAN_SET_NOBLOCKDELAY:
if (enable_set(dev))
return -1;
if (get_user(noblock_delay,(int *)arg))
return -EFAULT;
printk("noblock_delay=%d\n",noblock_delay);
break;
case CAN_SET_BAUDRATE:
printk("begin can_set_baudrate\n");
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
if (get_user(baud,(enum bau *)arg))
return -EFAULT;
set_baudrate(baud,dev->base_addr);
dev->parm->baud_rate=baud;
delay_by_baud=baud+1;
restore_flags(flag);
break;
case CAN_SET_AFM:
printk("begin can_set_afm\n");
if (get_user(afm,(int *)arg))
return -EFAULT;
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
set_AFM(afm?DOUBLE : SINGLE,dev->base_addr);
restore_flags(flag);
break;
case CAN_SET_STM:
printk("begin can_set_stm\n");
if (get_user(stm,(int *)arg))
return -EFAULT;
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
set_STM(stm?TOFF: TON ,dev->base_addr);
restore_flags(flag);
break;
case CAN_SET_LOM:
printk("begin can_set_lom\n");
if (get_user(lom,(int *)arg))
return -EFAULT;
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
set_LOM(lom?LOFF: LON ,dev->base_addr);
restore_flags(flag);
break;
case CAN_SET_SM:
printk("begin can_set_sm\n");
if (get_user(sm,(int *)arg))
return -EFAULT;
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
set_SM(sm?SOFF: SON ,dev->base_addr);
restore_flags(flag);
break;
case CAN_SET_FILTER:
printk("begin can_set_filter\n");
save_flags(flag);
cli();
if (enable_set(dev)) {
printk("some procees is sending or recving...,don't change it\n");
return -1;
}
filter=(struct filter_struct *)kmalloc(sizeof(struct filter_struct),
GFP_KERNEL);
memset(filter,0,sizeof(struct filter_struct));
if (copy_from_user(filter,(struct filter_struct *)arg,
sizeof(struct filter_struct)))
return -EFAULT;
set_FILTER(filter,dev->base_addr,0);
restore_flags(flag);
break;
case CAN_SET_FILTER1:
printk("begin can_set_filter1\n");
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
filter=(struct filter_struct *)kmalloc(sizeof(struct filter_struct),
GFP_KERNEL);
if (copy_from_user(filter,(struct filter_struct *)arg,
sizeof(struct filter_struct)))
return -EFAULT;
set_FILTER(filter,dev->base_addr,1);
restore_flags(flag);
break;
case CAN_SET_FILTER2:
printk("begin can_set_filter2\n");
save_flags(flag);
cli();
if (enable_set(dev))
return -1;
filter=(struct filter_struct *)kmalloc(sizeof(struct filter_struct),
GFP_KERNEL);
if (copy_from_user(filter,(struct filter_struct *)arg,
sizeof(struct filter_struct)))
return -EFAULT;
set_FILTER(filter,dev->base_addr,2);
restore_flags(flag);
break;
case CAN_GET_FILTER:
printk("begin can_get_filter\n");
filter=(struct filter_struct *)kmalloc(sizeof(struct filter_struct),
GFP_KERNEL);
memset(filter,0,sizeof(struct filter_struct));
read_FILTER(filter,dev->base_addr);
if (copy_to_user((struct filter_struct *)arg,filter,
sizeof(struct filter_struct)))
return -EFAULT;
break;
case CAN_GET_STATUS:
printk("begin read status\n");
status=read_status(dev->base_addr);
printk("in ioctl status=%d\n",status);
if (put_user(status,(int *)arg))
return -2;
dev->status=status;
break;
case CAN_GET_MODE:
printk("begin can_get_mode\n");
mode=(int)read_mode(dev->base_addr);
if (put_user(mode,(int *)arg))
return -EFAULT;
break;
case CAN_GET_BAUDRATE:
printk("begin can_get_baudrate\n");
switch (read_baudrate(dev->base_addr)) {
case 0:
baud= B1000;
break;
case 1:
baud= B800;
break;
case 2:
baud= B500;
break;
case 3:
baud= B320;
break;
case 4:
baud= B250;
break;
case 5:
baud= B160;
break;
case 6:
baud= B80;
break;
case 7:
baud= B40;
break;
case 8:
baud= B20;
break;
case 9:
baud= B10;
break;
case 10:
baud= B5;
default:
return -1;
}
if (put_user(baud,(enum bau *)arg)) return -EFAULT;
break;
case CAN_GET_ERRCOUNT:
printk("begin can_get_errcount\n");
err_count=read_err_counter(dev->base_addr);
if (put_user(err_count,(int *)arg)) return -EFAULT;
break;
case CAN_GET_ERRCAPTURE:
printk("begin can_get_errcapture\n");
err_capture=kmalloc(sizeof(struct err_cap_struct),GFP_KERNEL);
if (copy_from_user(err_capture,(struct err_cap_struct *)arg,
sizeof(struct err_cap_struct))) return -EFAULT;
read_err_capture(err_capture,dev->base_addr);
if (copy_to_user((struct err_cap_struct *)arg,err_capture,
sizeof(struct err_cap_struct)))
return -EFAULT;
break;
case CAN_GET_ARBCOUNT:
printk("begin can_get_arbcount\n");
arb_count=read_arb_counter(dev->base_addr);
if (put_user(arb_count,(int *)arg))
return -EFAULT;
break;
case CAN_GET_ARBCAPTURE:
printk("begin can_get_abrcapture\n");
arb_capture=kmalloc(sizeof(struct arb_cap_struct),GFP_KERNEL);
#if 0
copy_from_user_ret(arb_capture,(struct arb_cap_struct *)arg,
sizeof(struct arb_cap_struct),-EFAULT);
#else
if (copy_from_user(arb_capture,(struct arb_cap_struct *)arg,
sizeof(struct arb_cap_struct)))
return -EFAULT;
#endif
read_arb_capture(arb_capture,dev->base_addr);
if (copy_to_user((struct arb_cap_struct *)arg,arb_capture,
sizeof(struct arb_cap_struct)))
return -EFAULT;
break;
case CAN_RESET:
printk("begin can_reset\n");
reset_CAN(dev->base_addr);
break;
default:
printk("unkonwn command \n");
return -EINVAL;
}
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -