Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/193.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android Linux内核模块unix域套接字_Android_Linux_Sockets_Unix Socket - Fatal编程技术网

Android Linux内核模块unix域套接字

Android Linux内核模块unix域套接字,android,linux,sockets,unix-socket,Android,Linux,Sockets,Unix Socket,我试图在内核和用户空间之间共享数据。最终目标是将其移植到Android,因此我使用unix域套接字。(我不知道这是否是最好的选择) 我有一个内核模块作为套接字客户端,一个c程序作为套接字服务器。反之亦然,内核模块充当套接字服务器,c程序充当套接字客户端 程序非常简单。服务器只是向客户端发送一个字符串,然后打印出来 我运行server\u user.c,然后尝试使用insmod插入client\u module.ko。我得到以下错误: Kernel panic - not syncing: sta

我试图在内核和用户空间之间共享数据。最终目标是将其移植到Android,因此我使用unix域套接字。(我不知道这是否是最好的选择)

我有一个内核模块作为套接字客户端,一个c程序作为套接字服务器。反之亦然,内核模块充当套接字服务器,c程序充当套接字客户端

程序非常简单。服务器只是向客户端发送一个字符串,然后打印出来

我运行server\u user.c,然后尝试使用insmod插入client\u module.ko。我得到以下错误:

Kernel panic - not syncing: stack - protector: Kernel stack is corrupted in: ffffffffa0005157

drm-kms-helper: panic occurred, switching back to text console 
怎么了

模块服务器

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/socket.h>
#include <linux/net.h>
#include <linux/un.h>
#include <net/sock.h>

#define SOCK_PATH   "/tmp/usocket"
#define LISTEN      10

struct socket *sock = NULL;
struct socket *newsock = NULL;

static int __init server_module_init( void ) {

  int retval;
  char* string = "hello_world";

  struct sockaddr_un addr;
  struct msghdr msg;
  struct iovec iov;
  mm_segment_t oldfs;

  // create
  retval = sock_create(AF_UNIX, SOCK_STREAM, 0, &sock);

  memset(&addr, 0, sizeof(addr));
  addr.sun_family = AF_UNIX;
  strcpy(addr.sun_path, SOCK_PATH);

  // bind
  retval = sock->ops->bind(sock,(struct sockaddr *)&addr, sizeof(addr));

  // listen
  retval = sock->ops->listen(sock, LISTEN);

  //accept
  retval = sock->ops->accept(sock, newsock, 0);

  //sendmsg
  memset(&msg, 0, sizeof(msg));
  memset(&iov, 0, sizeof(iov));

  msg.msg_name = 0;
  msg.msg_namelen = 0;
  msg.msg_iov = &iov;
  msg.msg_iov->iov_base = string;
  msg.msg_iov->iov_len = strlen(string)+1;
  msg.msg_iovlen = 1;
  msg.msg_control = NULL;
  msg.msg_controllen = 0;
  msg.msg_flags = 0;

  oldfs = get_fs();
  set_fs(KERNEL_DS);

  retval = sock_sendmsg(newsock, &msg, strlen(string)+1);

  set_fs(oldfs);

  return 0;
}

static void __exit server_module_exit( void ) {
  printk(KERN_INFO "Exit usocket.");
}

module_init( server_module_init );
module_exit( server_module_exit );
MODULE_LICENSE("GPL");
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#定义SOCK_路径“/tmp/usocket”
#定义听10
结构套接字*sock=NULL;
结构套接字*newsock=NULL;
静态整数初始化服务器模块初始化(无效){
内部检索;
char*string=“hello\u world”;
结构sockaddr_un addr;
结构msghdr msg;
结构iovec iov;
mm_段_toldfs;
//创造
retval=sock\u create(AF\u UNIX、sock\u STREAM、0和sock);
memset(&addr,0,sizeof(addr));
addr.sun_family=AF_UNIX;
strcpy(addr.sun\u路径、SOCK\u路径);
//束缚
retval=sock->ops->bind(sock,(struct sockaddr*)和addr,sizeof(addr));
//听
retval=sock->ops->listen(sock,listen);
//接受
retval=sock->ops->accept(sock,newsock,0);
//sendmsg
memset(&msg,0,sizeof(msg));
memset(&iov,0,sizeof(iov));
msg.msg_name=0;
msg.msg_namelen=0;
msg.msg_iov=&iov;
msg.msg_iov->iov_base=string;
msg.msg_iov->iov_len=strlen(字符串)+1;
msg.msg_iovlen=1;
msg.msg_control=NULL;
msg.msg_controllen=0;
msg.msg_标志=0;
oldfs=get_fs();
set_fs(内核_DS);
retval=sock_sendmsg(newsock,&msg,strlen(string)+1);
set_fs(oldfs);
返回0;
}
静态无效\退出服务器\模块\退出(无效){
printk(KERN_INFO“Exit usocket.”);
}
模块初始化(服务器模块初始化);
模块退出(服务器模块退出);
模块许可证(“GPL”);
模块客户端

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/un.h>
#include <linux/net.h>
#include <net/sock.h>
#include <linux/socket.h>

#define SOCK_PATH   "/tmp/usocket"
#define MAX     100

struct socket *sock = NULL;


static int __init client_module_init( void ) {

  int retval;
  char str[MAX];

  struct sockaddr_un addr;
  struct msghdr msg;
  struct iovec iov;
  mm_segment_t oldfs;

  printk(KERN_INFO "Start client module.\n");

  // create
  retval = sock_create(AF_UNIX, SOCK_STREAM, 0, &sock); 

  // connect
  memset(&addr, 0, sizeof(addr));  
  addr.sun_family = AF_UNIX;
  strcpy(addr.sun_path, SOCK_PATH);

  retval = sock->ops->connect(sock, (struct sockaddr *)&addr, sizeof(addr), 0);

  // recvmsg

  memset(&msg, 0, sizeof(msg));
  memset(&iov, 0, sizeof(iov));

  msg.msg_name = 0;
  msg.msg_namelen = 0;
  msg.msg_iov = &iov;
  msg.msg_iovlen = 1;
  msg.msg_iov->iov_base= str;
  msg.msg_iov->iov_len= strlen(str)+1;
  msg.msg_control = NULL;
  msg.msg_controllen = 0;
  msg.msg_flags = 0;

  oldfs = get_fs();
  set_fs(KERNEL_DS);

  retval = sock_recvmsg(sock, &msg, strlen(str)+1, 0);

  set_fs(oldfs);

  // print str
  printk(KERN_INFO "client module: %s.\n",str);

  // release socket
  sock_release(sock);

  return 0;
}

static void __exit client_module_exit( void )
{
  printk(KERN_INFO "Exit client module.\n");
}

 module_init( client_module_init );
 module_exit( client_module_exit );
 MODULE_LICENSE("GPL");
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#定义SOCK_路径“/tmp/usocket”
#定义最大值100
结构套接字*sock=NULL;
静态整数初始化客户端模块初始化(无效){
内部检索;
字符str[MAX];
结构sockaddr_un addr;
结构msghdr msg;
结构iovec iov;
mm_段_toldfs;
printk(KERN_INFO“启动客户端模块。\n”);
//创造
retval=sock\u create(AF\u UNIX、sock\u STREAM、0和sock);
//连接
memset(&addr,0,sizeof(addr));
addr.sun_family=AF_UNIX;
strcpy(addr.sun\u路径、SOCK\u路径);
retval=sock->ops->connect(sock,(struct sockaddr*)和addr,sizeof(addr),0);
//recvmsg
memset(&msg,0,sizeof(msg));
memset(&iov,0,sizeof(iov));
msg.msg_name=0;
msg.msg_namelen=0;
msg.msg_iov=&iov;
msg.msg_iovlen=1;
msg.msg_iov->iov_base=str;
msg.msg_iov->iov_len=strlen(str)+1;
msg.msg_control=NULL;
msg.msg_controllen=0;
msg.msg_标志=0;
oldfs=get_fs();
set_fs(内核_DS);
retval=sock_recvmsg(sock,&msg,strlen(str)+1,0);
set_fs(oldfs);
//打印str
printk(内核信息“客户端模块:%s.\n”,str);
//释放插座
sock_释放(sock);
返回0;
}
静态无效\退出客户端\模块\退出(无效)
{
printk(KERN_INFO“退出客户端模块。\n”);
}
模块初始化(客户端模块初始化);
模块退出(客户端模块退出);
模块许可证(“GPL”);
用户服务器

#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/un.h>

#define SOCK_PATH "/tmp/usocket"

int send_msg_to_client(int socketfd, char* data) {

  struct msghdr msg;
  struct iovec iov;
  int s;

  memset(&msg, 0, sizeof(msg));
  memset(&iov, 0, sizeof(iov));

  msg.msg_name = NULL;
  msg.msg_namelen = 0;
  iov.iov_base = data;
  iov.iov_len = strlen(data)+1;
  msg.msg_iov = &iov;
  msg.msg_iovlen = 1;
  msg.msg_control = NULL;
  msg.msg_controllen = 0;
  msg.msg_flags = 0;

  s = sendmsg(socketfd, &msg, 0);

  printf("after send - iov_base: %s, length: %d\n", (char *) msg.msg_iov->iov_base, (int) strlen(msg.msg_iov->iov_base));

  if(s < 0){
    perror("sendmsg");
    return 0;
  }

  return s;
}


int main(int argc, char* argv[])
{

        if (argc != 2) {
          printf("Usage: $ %s <string>\n",argv[0]);
          return 0;
        }

    int s, s2, len, slen;
    socklen_t t;
    struct sockaddr_un local, remote;
    char* data = argv[1];

    printf("print data: %s\n",data);

    if ((s = socket(AF_UNIX, SOCK_STREAM, 0)) == -1) {
        perror("socket");
        exit(1);
    }

    memset(&local, 0, sizeof(local));
    local.sun_family = AF_UNIX;
    strcpy(local.sun_path, SOCK_PATH);

    unlink(local.sun_path);

    len = strlen(local.sun_path) + sizeof(local.sun_family);
    if (bind(s, (struct sockaddr *)&local, len) == -1) {
        perror("bind");
        exit(1);
    }

    if (listen(s, 5) == -1) {
        perror("listen");
        exit(1);
    }

    printf("Waiting for a connection...\n");

    t = sizeof(remote);
    if ((s2 = accept(s, (struct sockaddr *)&remote, &t)) == -1) {
        perror("accept");
        exit(1);
    }

    printf("Connected.\n");

    slen = send_msg_to_client(s2, data);

    if(slen < 0)
        perror("send");

    close(s2);

    return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#定义SOCK_路径“/tmp/usocket”
int发送消息到客户端(int socketfd,char*数据){
结构msghdr msg;
结构iovec iov;
int-s;
memset(&msg,0,sizeof(msg));
memset(&iov,0,sizeof(iov));
msg.msg_name=NULL;
msg.msg_namelen=0;
iov.iov_base=数据;
iov.iov_len=strlen(数据)+1;
msg.msg_iov=&iov;
msg.msg_iovlen=1;
msg.msg_control=NULL;
msg.msg_controllen=0;
msg.msg_标志=0;
s=sendmsg(socketfd和msg,0);
printf(“发送后-iov_base:%s,长度:%d\n”,(char*)msg.msg_iov->iov_base,(int)strlen(msg.msg_iov->iov_base));
如果(s<0){
perror(“sendmsg”);
返回0;
}
返回s;
}
int main(int argc,char*argv[])
{
如果(argc!=2){
printf(“用法:$%s\n”,argv[0]);
返回0;
}
内部s、s2、len、slen;
socklen_t;
结构sockaddr_un本地、远程;
char*data=argv[1];
printf(“打印数据:%s\n”,数据);
if((s=socket(AF_UNIX,SOCK_STREAM,0))=-1){
佩罗(“插座”);
出口(1);
}
memset(&local,0,sizeof(local));
local.sun_family=AF_UNIX;
strcpy(local.sun\u路径、SOCK\u路径);
取消链接(本地。新路);
len=strlen(local.sun_路径)+sizeof(local.sun_族);
if(绑定(s,(结构sockaddr*)和本地,len)=-1){
佩罗(“绑定”);
出口(1);
}
如果(听(s,5)=-1){
佩罗尔(“倾听”);
出口(1);
}
printf(“正在等待连接…\n”);
t=sizeof(远程);
if((s2=accept(s,(struct sockaddr*)和remote,&t))=-1){
佩罗(“接受”);
出口(1);
}
printf(“已连接。\n”);
slen=将消息发送至客户端(s2,数据);
if(slen<0)
佩罗(“发送”);
关闭(s2);
返回0;
}
用户客户端

#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/un.h>

#define SOCK_PATH "/tmp/usocket"
#define MAX 100

int recv_msg_from_server(int socketfd, char data[MAX]) {

  struct msghdr msg;
  struct iovec iov;
  int s;

  memset(&msg, 0, sizeof(msg));
  memset(&iov, 0, sizeof(iov));

  msg.msg_name = NULL;
  msg.msg_namelen = 0;
  iov.iov_base = data;
  iov.iov_len = MAX;
  msg.msg_iov = &iov;
  msg.msg_iovlen = 1;
  msg.msg_control = NULL;
  msg.msg_controllen = 0;
  msg.msg_flags = 0;


  s = recvmsg(socketfd, &msg, 0);

  printf("after recv - iov_base: %s, length: %d\n", (char *) msg.msg_iov->iov_base, (int) strlen(msg.msg_iov->iov_base));

  if(s < 0){
    perror("recvmsg");
  }

  return s;
}


int main(void)
{
    int s, len, slen;
    struct sockaddr_un remote;
    char data[MAX];

    if ((s = socket(AF_UNIX, SOCK_STREAM, 0)) == -1) {
            perror("socket");
            exit(1);
        }

    printf("Trying to connect...\n");

    memset(&remote, 0, sizeof(remote));

    remote.sun_family = AF_UNIX;
    strcpy(remote.sun_path, SOCK_PATH);
    len = strlen(remote.sun_path) + sizeof(remote.sun_family);

    if (connect(s, (struct sockaddr *)&remote, len) == -1) {
            perror("connect");
            exit(1);
        }

    printf("Connected.\n");

    slen = recv_msg_from_server(s, data);

    if (slen < 0) {
        perror("recvmsg");
    }

    //printf("print data received > %s\n", data);

    close(s);

    return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#包括
#定义SOCK_路径“/tmp/usocket”
#定义最大值100
来自服务器的int recv_msg_(int socketfd,字符数据[MAX]){
结构msghdr msg;
结构iovec iov;
int-s;
memset(&msg,0,sizeof(msg));
memset(&iov,0,sizeof(iov));
msg.msg_name=NULL;
msg.msg_namelen=0;
iov.iov_base=数据;
iov.iov_len=最大值;
msg.msg_iov=&iov;
msg.msg_iovlen=1;
msg.msg_control=NULL;
msg.msg_controllen=0;
msg.msg_标志=0;
s=recvmsg(socketfd和msg,0);
printf(“在recv-iov_base:%s之后,长度:%d\n”,(char*)msg.msg_iov->iov_base,(int)strlen(msg.msg_iov->iov_base));
如果(s<0){
struct sockaddr_storage addrStorage;
struct sockaddr_un* addr;
memset(&addrStorage, 0, sizeof(addrStorage));
addr = (struct sockaddr_un*)&addrStorage;
addr->sun_family = AF_UNIX;
strcpy(addr->sun_path, "/my/sock/name");
kernel_bind(listenSock, (struct sockaddr*)addr, sizeof(*addr));