@@ -56,6 +56,7 @@
#include <linux/wireless.h>
#include <linux/icmp.h>
#include <linux/icmpv6.h>
+#include <linux/can/raw.h>
#include <linux/errqueue.h>
#include <linux/random.h>
#ifdef CONFIG_TIMERFD
@@ -2111,6 +2112,39 @@ static abi_long do_setsockopt(int sockfd, int level, int optname,
goto unimplemented;
}
break;
+ case SOL_CAN_RAW:
+ switch (optname) {
+ case CAN_RAW_FILTER:
+ {
+ if (optlen % sizeof(struct can_filter) != 0) {
+ return -TARGET_EINVAL;
+ }
+
+ struct can_filter *can_filters = NULL;
+ if (optlen != 0) {
+ can_filters = g_new0(struct can_filter, optlen);
+
+ if (!can_filters) {
+ return -TARGET_ENOMEM;
+ }
+ if (copy_from_user(can_filters, optval_addr, optlen)) {
+ g_free(can_filters);
+ return -TARGET_EFAULT;
+ }
+ for (val = 0; val < optlen / sizeof(struct can_filter); val++) {
+ can_filters[val].can_id = tswap32(can_filters[val].can_id);
+ can_filters[val].can_mask = tswap32(can_filters[val].can_mask);
+ }
+ }
+ ret = get_errno(setsockopt(sockfd, level, optname,
+ can_filters, optlen));
+ g_free(can_filters);
+ break;
+ }
+ default:
+ goto unimplemented;
+ }
+ break;
case SOL_RAW:
switch (optname) {
case ICMP_FILTER:
Signed-off-by: Tomas Krcka <tomas.krcka@gmail.com> --- linux-user/syscall.c | 34 ++++++++++++++++++++++++++++++++++ 1 file changed, 34 insertions(+)