.func = vlan_skb_recv, /* VLAN receive method */
};
-/* Bits of netdev state that are propogated from real device to virtual */
+/* Bits of netdev state that are propagated from real device to virtual */
#define VLAN_LINK_STATE_MASK \
((1<<__LINK_STATE_PRESENT)|(1<<__LINK_STATE_NOCARRIER))
printk(KERN_ERR
"%s %s: can't create entry in proc filesystem!\n",
__FUNCTION__, VLAN_NAME);
- return 1;
+ return err;
}
dev_add_pack(&vlan_packet_type);
/* Register us to receive netdevice events */
- register_netdevice_notifier(&vlan_notifier_block);
+ err = register_netdevice_notifier(&vlan_notifier_block);
+ if (err < 0) {
+ dev_remove_pack(&vlan_packet_type);
+ vlan_proc_cleanup();
+ return err;
+ }
vlan_ioctl_set(vlan_ioctl_handler);
switch (event) {
case NETDEV_CHANGE:
- /* Propogate real device state to vlan devices */
+ /* Propagate real device state to vlan devices */
flgs = dev->state & VLAN_LINK_STATE_MASK;
for (i = 0; i < VLAN_GROUP_ARRAY_LEN; i++) {
vlandev = grp->vlan_devices[i];
static int vlan_ioctl_handler(void __user *arg)
{
int err = 0;
+ unsigned short vid = 0;
struct vlan_ioctl_args args;
- /* everything here needs root permissions, except aguably the
- * hack ioctls for sending packets. However, I know _I_ don't
- * want users running that on my network! --BLG
- */
- if (!capable(CAP_NET_ADMIN))
- return -EPERM;
-
if (copy_from_user(&args, arg, sizeof(struct vlan_ioctl_args)))
return -EFAULT;
switch (args.cmd) {
case SET_VLAN_INGRESS_PRIORITY_CMD:
+ if (!capable(CAP_NET_ADMIN))
+ return -EPERM;
err = vlan_dev_set_ingress_priority(args.device1,
args.u.skb_priority,
args.vlan_qos);
break;
case SET_VLAN_EGRESS_PRIORITY_CMD:
+ if (!capable(CAP_NET_ADMIN))
+ return -EPERM;
err = vlan_dev_set_egress_priority(args.device1,
args.u.skb_priority,
args.vlan_qos);
break;
case SET_VLAN_FLAG_CMD:
+ if (!capable(CAP_NET_ADMIN))
+ return -EPERM;
err = vlan_dev_set_vlan_flag(args.device1,
args.u.flag,
args.vlan_qos);
break;
case SET_VLAN_NAME_TYPE_CMD:
+ if (!capable(CAP_NET_ADMIN))
+ return -EPERM;
if ((args.u.name_type >= 0) &&
(args.u.name_type < VLAN_NAME_TYPE_HIGHEST)) {
vlan_name_type = args.u.name_type;
}
break;
- /* TODO: Figure out how to pass info back...
- case GET_VLAN_INGRESS_PRIORITY_IOCTL:
- err = vlan_dev_get_ingress_priority(args);
- break;
-
- case GET_VLAN_EGRESS_PRIORITY_IOCTL:
- err = vlan_dev_get_egress_priority(args);
- break;
- */
-
case ADD_VLAN_CMD:
+ if (!capable(CAP_NET_ADMIN))
+ return -EPERM;
/* we have been given the name of the Ethernet Device we want to
* talk to: args.dev1 We also have the
* VLAN ID: args.u.VID
break;
case DEL_VLAN_CMD:
+ if (!capable(CAP_NET_ADMIN))
+ return -EPERM;
/* Here, the args.dev1 is the actual VLAN we want
* to get rid of.
*/
err = unregister_vlan_device(args.device1);
break;
+ case GET_VLAN_INGRESS_PRIORITY_CMD:
+ /* TODO: Implement
+ err = vlan_dev_get_ingress_priority(args);
+ if (copy_to_user((void*)arg, &args,
+ sizeof(struct vlan_ioctl_args))) {
+ err = -EFAULT;
+ }
+ */
+ err = -EINVAL;
+ break;
+ case GET_VLAN_EGRESS_PRIORITY_CMD:
+ /* TODO: Implement
+ err = vlan_dev_get_egress_priority(args.device1, &(args.args);
+ if (copy_to_user((void*)arg, &args,
+ sizeof(struct vlan_ioctl_args))) {
+ err = -EFAULT;
+ }
+ */
+ err = -EINVAL;
+ break;
+ case GET_VLAN_REALDEV_NAME_CMD:
+ err = vlan_dev_get_realdev_name(args.device1, args.u.device2);
+ if (copy_to_user(arg, &args,
+ sizeof(struct vlan_ioctl_args))) {
+ err = -EFAULT;
+ }
+ break;
+
+ case GET_VLAN_VID_CMD:
+ err = vlan_dev_get_vid(args.device1, &vid);
+ args.u.VID = vid;
+ if (copy_to_user(arg, &args,
+ sizeof(struct vlan_ioctl_args))) {
+ err = -EFAULT;
+ }
+ break;
+
default:
/* pass on to underlying device instead?? */
printk(VLAN_DBG "%s: Unknown VLAN CMD: %x \n",