socketFun.c 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125
  1. #include <linux/init.h>
  2. #include <linux/module.h>
  3. #include <linux/kernel.h>
  4. #include <linux/mm_types.h>
  5. #include <linux/mm.h>
  6. #include <linux/gfp.h>
  7. #include <linux/sched.h>
  8. #include <linux/kthread.h>
  9. #include <linux/thread_info.h>
  10. #include <linux/net.h>
  11. #include <linux/socket.h>
  12. #include <net/sock.h>
  13. #include <linux/syscalls.h>
  14. #include <linux/file.h>
  15. #include <linux/ctype.h>
  16. #include <linux/types.h>
  17. #include <linux/audit.h>
  18. #include <linux/security.h>
  19. #include <asm/current.h>
  20. #include <linux/tcp.h>
  21. #include <net/tcp.h>
  22. #include <net/inet_common.h>
  23. #include <linux/uaccess.h>
  24. #include <asm/socket.h>
  25. #include "SOCK.h"
  26. MODULE_LICENSE("Dual BSD/GPL");
  27. enum {
  28. TZ_SOCKET = 0x0001,
  29. TZ_CONNECT,
  30. TZ_SEND,
  31. TZ_RECV,
  32. TZ_CLOSE,
  33. TZ_BIND,
  34. TZ_LISTEN,
  35. TZ_ACCEPT,
  36. TZ_INET_ADDR,
  37. TZ_HTONS,
  38. TZ_SETSOCKOPT,
  39. };
  40. #define ARGS_BLOCK_SIZE 1024
  41. #define TRUST_ZONE 0x0001
  42. #define NT_SMC_SWITCH 0 /* switch to T */
  43. #define NT_SMC_SWITCH_FIRST 0 /* first switch to T */
  44. #define NT_SMC_SWITCH_SECOND 1 /* for second time*/
  45. #define Asm (__asm__ volatile)
  46. #define SOCKET_BASE 0xFE021000
  47. enum {
  48. FUCTION_socket = 0x0,
  49. FUCTION_connect = 0x04,
  50. FUCTION_send = 0x08,
  51. FUCTION_recv = 0x0C,
  52. FUCTION_close = 0x20,
  53. FUNCTION_setsockopt = 0x24,
  54. SET_BUFFER_BASE = 0xF0,
  55. SET_PARAM_BASE = 0xF4,
  56. };
  57. struct socket_params_t {
  58. int domain;
  59. int type;
  60. int protocol;
  61. long returns;
  62. } __attribute__((__packed__));
  63. struct connect_params_t {
  64. int sockfd;
  65. struct sockaddr addr;
  66. int addrlen;
  67. long returns;
  68. } __attribute__((__packed__));
  69. struct send_params_t {
  70. int sockfd;
  71. size_t len;
  72. int flags;
  73. long returns;
  74. } __attribute__((__packed__));
  75. struct recv_params_t {
  76. int sockfd;
  77. size_t len;
  78. int flags;
  79. long returns;
  80. } __attribute__((__packed__));
  81. struct close_params_t {
  82. int sockfd;
  83. long returns;
  84. } __attribute__((__packed__));
  85. struct TEEI_socket_command {
  86. int func;
  87. int cmd_size;
  88. union func_arg {
  89. char raw[ARGS_BLOCK_SIZE];
  90. struct func_socket {
  91. int af;
  92. int type;
  93. int protocol;
  94. } func_socket_args;
  95. struct func_connect {
  96. int sockfd;
  97. struct sockaddr ob_addr;
  98. int addrlen;
  99. } func_connect_args;
  100. struct func_bind {
  101. int sockfd;
  102. struct sockaddr ob_addr;
  103. int addrlen;
  104. } func_bind_args;
  105. struct func_listen {
  106. int sockfd;
  107. int backlog;
  108. } func_listen_args;
  109. struct func_accept {
  110. int sockfd;
  111. struct sockaddr ob_addr;
  112. int addrlen;
  113. } func_accept_args;
  114. struct func_send {
  115. int sockfd;
  116. void *buf;
  117. int len;
  118. int flags;
  119. } func_send_args;
  120. #define func_recv func_send
  121. #define func_recv_args func_send_args
  122. #define func_recv_send func_send
  123. #define func_recv_send_args func_send_args
  124. struct func_close {
  125. int sockfd;
  126. } func_close_args;
  127. struct func_inet_addr {
  128. char ip_addr[17];
  129. } func_inet_addr_args;
  130. struct func_htons {
  131. unsigned short portnum;
  132. } func_htons_args;
  133. struct func_setsockopt {
  134. int sockfd;
  135. int level;
  136. int optname;
  137. int optlen;
  138. } func_setsockopt_args;
  139. } args;
  140. };
  141. union TEEI_socket_response_type {
  142. int value;
  143. uint32_t addr;
  144. bool hasError;
  145. unsigned short portnum;
  146. unsigned int transSize;
  147. struct response_func_recv {
  148. void *buf;
  149. unsigned int size;
  150. } recv;
  151. };
  152. /******************************************************************
  153. * @brief:
  154. * smc call()
  155. * @param:
  156. * p1 - param 1 cmd type
  157. * p2 - param 2 first or second switch
  158. * p3 - param 3 transfer data address (PA)
  159. * p4 - param 4 extern value
  160. * @return:
  161. * *****************************************************************/
  162. static void smc_call(uint32_t p1, uint32_t p2, uint32_t p3, uint32_t p4)
  163. {
  164. pr_info("********* go to secure world!\n");
  165. Asm("mov r0, %0\n\t"
  166. "mov r1, %1\n\t"
  167. "mov r2, %2\n\t"
  168. "mov r3, %3\n\t"
  169. "smc 0\n\t"
  170. : /*no output*/
  171. : "r" (p1), "r" (p2), "r" (p3), "r" (p4)
  172. : "r0", "r1", "r2", "r3", "memory");
  173. pr_info("********** back form secure world !\n");
  174. }
  175. int tz_inet_aton(char *cp, struct in_addr *addr)
  176. {
  177. register u_long val;
  178. register int base, n;
  179. register char c;
  180. u_int parts[4];
  181. register u_int *pp = parts;
  182. c = *cp;
  183. for (;;) {
  184. /*
  185. * Collect number up to ``.''.
  186. * Values are specified as for C:
  187. * 0x=hex, 0=octal, isdigit=decimal.
  188. */
  189. if (!isdigit(c))
  190. return 0;
  191. val = 0;
  192. base = 10;
  193. if (c == '0') {
  194. c = *++cp;
  195. if (c == 'x' || c == 'X')
  196. base = 16, c = *++cp;
  197. else
  198. base = 8;
  199. }
  200. for (;;) {
  201. if (isascii(c) && isdigit(c)) {
  202. val = (val * base) + (c - '0');
  203. c = *++cp;
  204. } else if (base == 16 && isascii(c) && isxdigit(c)) {
  205. val = (val << 4) |
  206. (c + 10 - (islower(c) ? 'a' : 'A'));
  207. c = *++cp;
  208. } else
  209. break;
  210. }
  211. if (c == '.') {
  212. /*
  213. * Internet format:
  214. * a.b.c.d
  215. * a.b.c (with c treated as 16 bits)
  216. * a.b (with b treated as 24 bits)
  217. */
  218. if (pp >= parts + 3)
  219. return 0;
  220. *pp++ = val;
  221. c = *++cp;
  222. } else
  223. break;
  224. }
  225. /*
  226. * Check for trailing characters.
  227. */
  228. if (c != '\0' && (!isascii(c) || !isspace(c)))
  229. return 0;
  230. /*
  231. * Concoct the address according to
  232. * the number of parts specified.
  233. */
  234. n = pp - parts + 1;
  235. switch (n) {
  236. case 0:
  237. return 0; /* initial nondigit */
  238. case 1: /* a -- 32 bits */
  239. break;
  240. case 2: /* a.b -- 8.24 bits */
  241. if (val > 0xffffff)
  242. return 0;
  243. val |= parts[0] << 24;
  244. break;
  245. case 3: /* a.b.c -- 8.8.16 bits */
  246. if (val > 0xffff)
  247. return 0;
  248. val |= (parts[0] << 24) | (parts[1] << 16);
  249. break;
  250. case 4: /* a.b.c.d -- 8.8.8.8 bits */
  251. if (val > 0xff)
  252. return 0;
  253. val |= (parts[0] << 24) | (parts[1] << 16) | (parts[2] << 8);
  254. break;
  255. }
  256. if (addr)
  257. addr->s_addr = htonl(val);
  258. return 1;
  259. }
  260. EXPORT_SYMBOL(tz_inet_aton);
  261. /*
  262. * Ascii internet address interpretation routine.
  263. * The value returned is in network order.
  264. */
  265. /* inet_addr */
  266. long tz_inet_addr(char *cp)
  267. {
  268. struct in_addr val;
  269. if (tz_inet_aton(cp, &val))
  270. return val.s_addr;
  271. return INADDR_NONE;
  272. }
  273. EXPORT_SYMBOL(tz_inet_addr);
  274. int tz_socket(int family, int type, int protocol, unsigned long para_address, unsigned long buffer_addr)
  275. {
  276. #ifdef QEMU
  277. int retval = 0;
  278. struct socket_params_t *sock_para = NULL;
  279. sock_para = kmalloc(sizeof(struct socket_params_t), GFP_KERNEL);
  280. memset(sock_para, 0, sizeof(struct socket_params_t));
  281. sock_para->domain = family;
  282. sock_para->type = type;
  283. sock_para->protocol = protocol;
  284. memcpy(para_address, sock_para, sizeof(struct socket_params_t));
  285. writel(0x00, SOCKET_BASE + FUCTION_socket);
  286. retval = ((struct socket_params_t *)para_address)->returns;
  287. kfree(sock_para);
  288. pr_info("socket function return value = %d\n", retval);
  289. #else
  290. int retval = 0;
  291. struct socket *sock = NULL;
  292. int flags = 0;
  293. /* Check the SOCK_* constants for consistency. */
  294. BUILD_BUG_ON(SOCK_CLOEXEC != O_CLOEXEC);
  295. BUILD_BUG_ON((SOCK_MAX | SOCK_TYPE_MASK) != SOCK_TYPE_MASK);
  296. BUILD_BUG_ON(SOCK_CLOEXEC & SOCK_TYPE_MASK);
  297. BUILD_BUG_ON(SOCK_NONBLOCK & SOCK_TYPE_MASK);
  298. flags = type & ~SOCK_TYPE_MASK;
  299. if (flags & ~(SOCK_CLOEXEC | SOCK_NONBLOCK))
  300. return -EINVAL;
  301. type &= SOCK_TYPE_MASK;
  302. if (SOCK_NONBLOCK != O_NONBLOCK && (flags & SOCK_NONBLOCK))
  303. flags = (flags & ~SOCK_NONBLOCK) | O_NONBLOCK;
  304. /* pr_info("---tz_socket family = %d, type = %d, protocol = %d\n", family, type, protocol); */
  305. retval = sock_create(family, type, protocol, &sock);
  306. if (retval < 0)
  307. goto out;
  308. /* retval = sock_map_fd(sock, flags & (O_CLOEXEC | O_NONBLOCK)); */
  309. if (retval < 0)
  310. goto out_release;
  311. out:
  312. /* It may be already another descriptor 8) Not kernel problem. */
  313. return retval;
  314. out_release:
  315. sock_release(sock);
  316. return retval;
  317. #endif
  318. return retval;
  319. }
  320. EXPORT_SYMBOL(tz_socket);
  321. int tz_htons(unsigned short int h)
  322. {
  323. return htons(h);
  324. }
  325. static struct socket *tz_sockfd_lookup_light(int fd, int *err, int *fput_needed)
  326. {
  327. struct file *file;
  328. struct socket *sock;
  329. *err = -EBADF;
  330. file = fget_light(fd, fput_needed);
  331. if (file) {
  332. sock = sock_from_file(file, err);
  333. if (sock)
  334. return sock;
  335. fput_light(file, *fput_needed);
  336. }
  337. return NULL;
  338. }
  339. /* ======================== tz_connect ===========================
  340. * Attempt to connect to a socket with the server address. The address
  341. * is in kernel space.
  342. */
  343. int tz_connect(int fd, struct sockaddr *address, int addrlen, unsigned long para_address, unsigned long buffer_addr)
  344. {
  345. #ifdef QEMU
  346. int retval = 0;
  347. struct connect_params_t *connect_para = NULL;
  348. connect_para = kmalloc(sizeof(struct connect_params_t), GFP_KERNEL);
  349. memset(connect_para, 0, sizeof(struct connect_params_t));
  350. connect_para->sockfd = fd;
  351. memcpy(&(connect_para->addr), address, addrlen);
  352. connect_para->addrlen = addrlen;
  353. memcpy(para_address, connect_para, sizeof(struct connect_params_t));
  354. writel(0x00, SOCKET_BASE+FUCTION_connect);
  355. retval = ((struct connect_params_t *)para_address)->returns;
  356. pr_info("connect function return value = %d\n", retval);
  357. kfree(connect_para);
  358. return retval;
  359. #else
  360. struct socket *sock;
  361. int err, fput_needed;
  362. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  363. if (!sock)
  364. goto out;
  365. err = sock->ops->connect(sock, (struct sockaddr *)address, addrlen,
  366. sock->file->f_flags);
  367. /* This function is in the net/ipv4/af_inet.c file. */
  368. fput_light(sock->file, fput_needed);
  369. out:
  370. return err;
  371. #endif
  372. }
  373. EXPORT_SYMBOL(tz_connect);
  374. /* ======================== tz_bind ===========================
  375. * Bind a name to a socket. Nothing much to do here since it's
  376. * the protocol's responsibility to handle the local address.
  377. *
  378. * We move the socket address to kernel space before we call
  379. * the protocol layer (having also checked the address is ok).
  380. */
  381. int tz_bind(int fd, struct sockaddr *addr, int addrlen)
  382. {
  383. struct socket *sock;
  384. int err, fput_needed;
  385. err = 0;
  386. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  387. if (sock) {
  388. err = sock->ops->bind(sock, (struct sockaddr *)addr, addrlen);
  389. fput_light(sock->file, fput_needed);
  390. }
  391. return err;
  392. }
  393. /* ======================== tz_bind ===========================
  394. * Perform a listen. Basically, we allow the protocol to do anything
  395. * necessary for a listen, and if that works, we mark the socket as
  396. * ready for listening.
  397. */
  398. int tz_listen(int fd, int backlog)
  399. {
  400. struct socket *sock;
  401. int err, fput_needed;
  402. int somaxconn;
  403. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  404. if (sock) {
  405. somaxconn = sock_net(sock->sk)->core.sysctl_somaxconn;
  406. if ((unsigned int)backlog > somaxconn)
  407. backlog = somaxconn;
  408. err = sock->ops->listen(sock, backlog);
  409. fput_light(sock->file, fput_needed);
  410. }
  411. return err;
  412. }
  413. /* ========================= tz_zone sys_accept ===================
  414. * For accept, we attempt to create a new socket, set up the link
  415. * with the client, wake up the client, then return the new
  416. * connected fd. We collect the address of the connector in kernel
  417. * space and move it to user at the very end. This is unclean because
  418. * we open the socket then return an error.
  419. *
  420. * 1003.1g adds the ability to recvmsg() to query connection pending
  421. * status to recvmsg. We need to add that support in a way thats
  422. * clean when we restucture accept also.
  423. */
  424. int tz_accept4(int fd, struct sockaddr *upeer_sockaddr,
  425. int *upeer_addrlen, int flags)
  426. {
  427. struct socket *sock, *newsock;
  428. struct file *newfile;
  429. int err, len, newfd, fput_needed, cpylen;
  430. struct sockaddr_storage address;
  431. if (flags & ~(SOCK_CLOEXEC | SOCK_NONBLOCK))
  432. return -EINVAL;
  433. if (SOCK_NONBLOCK != O_NONBLOCK && (flags & SOCK_NONBLOCK))
  434. flags = (flags & ~SOCK_NONBLOCK) | O_NONBLOCK;
  435. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  436. if (!sock)
  437. goto out;
  438. err = -ENFILE;
  439. newsock = sock_alloc();
  440. if (NULL == newsock)
  441. goto out_put;
  442. newsock->type = sock->type;
  443. newsock->ops = sock->ops;
  444. /*
  445. * We don't need try_module_get here, as the listening socket (sock)
  446. * has the protocol module (sock->ops->owner) held.
  447. */
  448. __module_get(newsock->ops->owner);
  449. /*
  450. * FIXME Do not has this function.
  451. * newfd = sock_alloc_file(newsock, &newfile, flags);
  452. */
  453. #ifdef QEMU
  454. newfd = sock_alloc_fd(&newfile, flags);
  455. #else
  456. newfd = sock_alloc_file(newsock, &newfile, flags);
  457. #endif
  458. if (unlikely(newfd < 0)) {
  459. err = newfd;
  460. sock_release(newsock);
  461. goto out_put;
  462. }
  463. #ifdef QEMU
  464. err = sock_attach_fd(newsock, newfile, flags);
  465. if (err < 0)
  466. goto out_fd_simple;
  467. #endif
  468. err = security_socket_accept(sock, newsock);
  469. if (err)
  470. goto out_fd;
  471. err = sock->ops->accept(sock, newsock, sock->file->f_flags);
  472. if (err < 0)
  473. goto out_fd;
  474. if (upeer_sockaddr) {
  475. if (newsock->ops->getname(newsock, (struct sockaddr *)&address,
  476. &len, 2) < 0) {
  477. err = -ECONNABORTED;
  478. goto out_fd;
  479. }
  480. /* copy socket address between kernel space.*/
  481. if (len > *upeer_addrlen)
  482. cpylen = *upeer_addrlen;
  483. else
  484. cpylen = len;
  485. memcpy(upeer_sockaddr, (struct sockaddr *)&address, cpylen);
  486. }
  487. /* File flags are not inherited via accept() unlike another OSes. */
  488. fd_install(newfd, newfile);
  489. err = newfd;
  490. out_put:
  491. fput_light(sock->file, fput_needed);
  492. out:
  493. return err;
  494. out_fd_simple:
  495. sock_release(newsock);
  496. put_filp(newfile);
  497. put_unused_fd(newfd);
  498. goto out_put;
  499. out_fd:
  500. fput(newfile);
  501. put_unused_fd(newfd);
  502. goto out_put;
  503. }
  504. int tz_accept(int fd, struct sockaddr *upeer_sockaddr, int *upeer_addrlen)
  505. {
  506. return tz_accept4(fd, upeer_sockaddr, upeer_addrlen, 0);
  507. }
  508. /* ==================== tz_send ========================== */
  509. int tz_sendto(int fd, void *buff, size_t len, unsigned int flags, struct sockaddr *addr, int addr_len)
  510. {
  511. struct socket *sock;
  512. int err;
  513. struct msghdr msg;
  514. struct iovec iov;
  515. int fput_needed;
  516. if (len > INT_MAX)
  517. len = INT_MAX;
  518. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  519. if (!sock)
  520. goto out;
  521. iov.iov_base = buff;
  522. iov.iov_len = len;
  523. msg.msg_name = NULL;
  524. msg.msg_iov = &iov;
  525. msg.msg_iovlen = 1;
  526. msg.msg_control = NULL;
  527. msg.msg_controllen = 0;
  528. msg.msg_namelen = 0;
  529. if (addr) {
  530. msg.msg_name = (struct sockaddr *)addr;
  531. msg.msg_namelen = addr_len;
  532. }
  533. if (sock->file->f_flags & O_NONBLOCK)
  534. flags |= MSG_DONTWAIT;
  535. msg.msg_flags = flags;
  536. err = sock_sendmsg(sock, &msg, len);
  537. fput_light(sock->file, fput_needed);
  538. out:
  539. return err;
  540. }
  541. /*
  542. * Send a datagram down a socket.
  543. */
  544. int tz_send(int fd, void *buff, size_t len, unsigned int flags, unsigned long para_address, unsigned long buffer_addr)
  545. {
  546. #ifdef QEMU
  547. int retval = 0;
  548. struct send_params_t *send_para = NULL;
  549. send_para = kmalloc(sizeof(struct send_params_t), GFP_KERNEL);
  550. memset(send_para, 0, sizeof(struct send_params_t));
  551. send_para->sockfd = fd;
  552. memcpy(buffer_addr, buff, len);
  553. send_para->len = len;
  554. send_para->flags = flags;
  555. memcpy(para_address, send_para, sizeof(struct send_params_t));
  556. writel(0x00, SOCKET_BASE + FUCTION_send);
  557. retval = ((struct send_params_t *)para_address)->returns;
  558. pr_info("send function return value = %d\n", retval);
  559. kfree(send_para);
  560. return retval;
  561. #else
  562. long ret;
  563. mm_segment_t old_fs;
  564. old_fs = get_fs();
  565. set_fs(get_ds());
  566. ret = sys_sendto(fd, buff, len, flags, NULL, 0);
  567. set_fs(old_fs);
  568. mdelay(10);
  569. return ret;
  570. #endif
  571. }
  572. EXPORT_SYMBOL(tz_send);
  573. /********************************************************************
  574. * tz_recv *
  575. ********************************************************************/
  576. int tz_recvfrom(int fd, void *ubuf, size_t size,
  577. unsigned flags, struct sockaddr *addr,
  578. int *addr_len)
  579. {
  580. struct socket *sock;
  581. struct iovec iov;
  582. struct msghdr msg;
  583. struct sockaddr_storage address;
  584. int err;
  585. int cpylen;
  586. int fput_needed;
  587. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  588. if (!sock)
  589. goto out;
  590. msg.msg_control = NULL;
  591. msg.msg_controllen = 0;
  592. msg.msg_iovlen = 1;
  593. msg.msg_iov = &iov;
  594. iov.iov_len = size;
  595. iov.iov_base = ubuf;
  596. msg.msg_name = (struct sockaddr *)&address;
  597. msg.msg_namelen = sizeof(address);
  598. if (sock->file->f_flags & O_NONBLOCK)
  599. flags |= MSG_DONTWAIT;
  600. err = sock_recvmsg(sock, &msg, size, flags);
  601. pr_info("the err is %d\n", err);
  602. if (err >= 0 && addr != NULL) {
  603. if (msg.msg_namelen > *addr_len)
  604. cpylen = *addr_len;
  605. else
  606. cpylen = msg.msg_namelen;
  607. memcpy(addr, &address, cpylen);
  608. }
  609. fput_light(sock->file, fput_needed);
  610. out:
  611. return err;
  612. }
  613. /***********************************************************************
  614. * Receive a datagram from a socket.
  615. ***********************************************************************/
  616. asmlinkage long tz_recv(int fd, void *ubuf, size_t size,
  617. unsigned flags, unsigned long para_address, unsigned long buffer_addr)
  618. {
  619. #ifdef QEMU
  620. int retval = 0;
  621. struct recv_params_t *recv_para = NULL;
  622. recv_para = kmalloc(sizeof(struct recv_params_t), GFP_KERNEL);
  623. memset(recv_para, 0, sizeof(struct recv_params_t));
  624. recv_para->sockfd = fd;
  625. /* memcpy(buffer_addr, buff, len); */
  626. recv_para->len = size;
  627. recv_para->flags = flags;
  628. memcpy(para_address, recv_para, sizeof(struct recv_params_t));
  629. writel(0x00, SOCKET_BASE+FUCTION_recv);
  630. retval = ((struct recv_params_t *)para_address)->returns;
  631. pr_info("recv function return value = %d\n", retval);
  632. if (retval > 0)
  633. memcpy(ubuf, buffer_addr, retval);
  634. kfree(recv_para);
  635. return retval;
  636. #else
  637. /* return tz_recvfrom(fd, ubuf, size, flags, NULL, NULL); */
  638. long ret;
  639. mm_segment_t old_fs;
  640. old_fs = get_fs();
  641. set_fs(get_ds());
  642. ret = sys_recvfrom(fd, ubuf, size, flags, NULL, NULL);
  643. /* pr_info(">>>>>>>>>>>>>>> recv length is %d bytes <<<<<<<<<<<<<<<<<<<<\n", ret); */
  644. set_fs(old_fs);
  645. return ret;
  646. #endif
  647. }
  648. EXPORT_SYMBOL(tz_recv);
  649. int tz_setsocketopt(int fd, int level, int optname, char *optval,
  650. int optlen, unsigned long para_address, unsigned long buffer_addr)
  651. {
  652. int err, fput_needed;
  653. struct socket *sock;
  654. if (optlen < 0)
  655. return -EINVAL;
  656. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  657. if (sock != NULL) {
  658. if (level == SOL_SOCKET)
  659. err = sock_setsockopt(sock, level, optname, optval, optlen);
  660. else
  661. err = sock->ops->setsockopt(sock, level, optname, optval, optlen);
  662. fput_light(sock->file, fput_needed);
  663. }
  664. return err;
  665. }
  666. int tz_shutdown(int fd, int how)
  667. {
  668. int err, fput_needed;
  669. struct socket *sock;
  670. sock = tz_sockfd_lookup_light(fd, &err, &fput_needed);
  671. if (sock != NULL) {
  672. err = security_socket_shutdown(sock, how);
  673. if (!err)
  674. err = sock->ops->shutdown(sock, how);
  675. fput_light(sock->file, fput_needed);
  676. }
  677. return err;
  678. }
  679. asmlinkage long tz_close(int fd, unsigned long para_address, unsigned long buffer_addr)
  680. {
  681. #if 0
  682. int retval = 0;
  683. struct close_params_t *close_para = NULL;
  684. close_para = kmalloc(sizeof(struct close_params_t), GFP_KERNEL);
  685. memset(close_para, 0, sizeof(struct close_params_t));
  686. close_para->sockfd = fd;
  687. memcpy(para_address, close_para, sizeof(struct close_params_t));
  688. writel(0x00, SOCKET_BASE+FUCTION_close);
  689. retval = ((struct close_params_t *)para_address)->returns;
  690. pr_info("close function return value = %d\n", retval);
  691. kfree(close_para);
  692. return retval;
  693. #else
  694. return sys_close(fd);
  695. #endif
  696. }
  697. EXPORT_SYMBOL(tz_close);
  698. void Worldtransport(int world_name, unsigned long phy_addr)
  699. {
  700. if (TRUST_ZONE == world_name)
  701. smc_call(NT_SMC_SWITCH, NT_SMC_SWITCH_SECOND, phy_addr, 0);
  702. return;
  703. }
  704. /**********************************************************************
  705. * socket_thread_function
  706. **********************************************************************/
  707. int socket_thread_function(unsigned long virt_addr, unsigned long para_vaddr, unsigned long buff_vaddr)
  708. {
  709. #if 1
  710. unsigned long sendRecv_address;
  711. unsigned long setsockopt_address;
  712. long retVal = 0;
  713. struct TEEI_socket_command *tz_command;
  714. union TEEI_socket_response_type tz_response;
  715. /* virt_addr = (unsigned long)__va(phy_addr); */
  716. /*
  717. memset(mem_head, '\0', sizeof(mem_head));
  718. memcpy(mem_head, (void*)virt_addr, sizeof(mem_head));
  719. functionCode = mem_head[0];
  720. commandLength = mem_head[1];
  721. memset(&tz_command, '\0', commandLength);
  722. memcpy(&tz_command, (void*)virt_addr, commandLength);
  723. */
  724. tz_command = (struct TEEI_socket_command *)virt_addr;
  725. /* pr_info(" come into the socket_thread_function, %x in %p\n", tz_command->func, &(tz_command->func)); */
  726. switch (tz_command->func) {
  727. case TZ_SOCKET:
  728. /* pr_info(" come into the SOCKET branch\n"); */
  729. retVal = tz_socket(tz_command->args.func_socket_args.af,
  730. tz_command->args.func_socket_args.type,
  731. tz_command->args.func_socket_args.protocol,
  732. para_vaddr,
  733. buff_vaddr);
  734. memset(&tz_response, '\0', sizeof(tz_response));
  735. tz_response.value = retVal;
  736. memset((void *)virt_addr, '\0', sizeof(tz_response));
  737. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  738. break;
  739. case TZ_HTONS:
  740. /* pr_info(" come into the TZ_HTONS branch\n"); */
  741. retVal = tz_htons(tz_command->args.func_htons_args.portnum);
  742. memset(&tz_response, '\0', sizeof(tz_response));
  743. tz_response.portnum = retVal;
  744. memset((void *)virt_addr, '\0', sizeof(tz_response));
  745. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  746. break;
  747. case TZ_INET_ADDR:
  748. /* pr_info(" come into the TZ_INET_ADDR branch\n"); */
  749. retVal = tz_inet_addr(tz_command->args.func_inet_addr_args.ip_addr);
  750. memset(&tz_response, '\0', sizeof(tz_response));
  751. tz_response.addr = retVal;
  752. memset((void *)virt_addr, '\0', sizeof(tz_response));
  753. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  754. break;
  755. case TZ_CONNECT:
  756. /* pr_info(" come into the TZ_CONNECT branch\n"); */
  757. retVal = tz_connect(tz_command->args.func_connect_args.sockfd,
  758. (struct sockaddr *)&(tz_command->args.func_connect_args.ob_addr),
  759. tz_command->args.func_connect_args.addrlen,
  760. para_vaddr,
  761. buff_vaddr);
  762. memset(&tz_response, '\0', sizeof(tz_response));
  763. tz_response.addr = retVal;
  764. memset((void *)virt_addr, '\0', sizeof(tz_response));
  765. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  766. break;
  767. case TZ_BIND:
  768. /* pr_info(" come into the TZ_BIND branch\n"); */
  769. retVal = tz_bind(tz_command->args.func_bind_args.sockfd,
  770. (struct sockaddr *)&(tz_command->args.func_bind_args.ob_addr),
  771. tz_command->args.func_bind_args.addrlen);
  772. memset(&tz_response, '\0', sizeof(tz_response));
  773. tz_response.value = retVal;
  774. memset((void *)virt_addr, '\0', sizeof(tz_response));
  775. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  776. break;
  777. case TZ_LISTEN:
  778. /* pr_info(" come into the TZ_LISTEN branch\n"); */
  779. retVal = tz_listen(tz_command->args.func_listen_args.sockfd,
  780. tz_command->args.func_listen_args.backlog);
  781. memset(&tz_response, '\0', sizeof(tz_response));
  782. tz_response.value = retVal;
  783. memset((void *)virt_addr, '\0', sizeof(tz_response));
  784. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  785. break;
  786. case TZ_ACCEPT:
  787. /* pr_info(" come into the TZ_ACCEPT branch\n"); */
  788. retVal = tz_accept(tz_command->args.func_accept_args.sockfd,
  789. (struct sockaddr *)&(tz_command->args.func_accept_args.ob_addr),
  790. &(tz_command->args.func_accept_args.addrlen));
  791. memset(&tz_response, '\0', sizeof(tz_response));
  792. tz_response.value = retVal;
  793. memset((void *)virt_addr, '\0', sizeof(tz_response));
  794. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  795. break;
  796. case TZ_RECV:
  797. /* pr_info(" come into the TZ_RECV branch\n"); */
  798. sendRecv_address = 0;
  799. sendRecv_address = kmalloc(tz_command->args.func_recv_args.len, GFP_KERNEL);
  800. retVal = tz_recv(tz_command->args.func_recv_args.sockfd,
  801. (void *)sendRecv_address,
  802. tz_command->args.func_recv_args.len,
  803. tz_command->args.func_recv_args.flags,
  804. para_vaddr,
  805. buff_vaddr);
  806. memset(&tz_response, '\0', sizeof(tz_response));
  807. tz_response.recv.size = retVal;
  808. tz_response.recv.buf = (void *)sendRecv_address;
  809. if (retVal > 0)
  810. memset((void *)virt_addr, '\0', sizeof(tz_response) + retVal);
  811. else
  812. memset((void *)virt_addr, '\0', sizeof(tz_response));
  813. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  814. if (retVal > 0)
  815. memcpy((void *)(virt_addr + sizeof(tz_response)), (void *)sendRecv_address, retVal);
  816. if (sendRecv_address != NULL)
  817. kfree(sendRecv_address);
  818. break;
  819. case TZ_SEND:
  820. sendRecv_address = 0;
  821. sendRecv_address = (unsigned long)(tz_command) + sizeof(struct TEEI_socket_command);
  822. retVal = tz_send(tz_command->args.func_send_args.sockfd,
  823. (void *)sendRecv_address,
  824. tz_command->args.func_send_args.len,
  825. tz_command->args.func_send_args.flags,
  826. para_vaddr,
  827. buff_vaddr);
  828. memset(&tz_response, '\0', sizeof(tz_response));
  829. tz_response.value = retVal;
  830. memset((void *)virt_addr, '\0', sizeof(tz_response));
  831. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  832. break;
  833. case TZ_CLOSE:
  834. retVal = tz_close(tz_command->args.func_close_args.sockfd, para_vaddr, buff_vaddr);
  835. memset(&tz_response, '\0', sizeof(tz_response));
  836. tz_response.value = retVal;
  837. memset((void *)virt_addr, '\0', sizeof(tz_response));
  838. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  839. break;
  840. case TZ_SETSOCKOPT:
  841. setsockopt_address = 0;
  842. setsockopt_address = (unsigned long)(tz_command) + sizeof(struct TEEI_socket_command);
  843. retVal = tz_setsocketopt(tz_command->args.func_setsockopt_args.sockfd,
  844. tz_command->args.func_setsockopt_args.level,
  845. tz_command->args.func_setsockopt_args.optname,
  846. setsockopt_address,
  847. tz_command->args.func_setsockopt_args.optlen,
  848. para_vaddr, buff_vaddr);
  849. memset(&tz_response, '\0', sizeof(tz_response));
  850. tz_response.value = retVal;
  851. memset((void *)virt_addr, '\0', sizeof(tz_response));
  852. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  853. break;
  854. default:
  855. memset(&tz_response, '\0', sizeof(tz_response));
  856. tz_response.value = EOPNOTSUPP;
  857. memset((void *)virt_addr, '\0', sizeof(tz_response));
  858. memcpy((void *)virt_addr, &tz_response, sizeof(tz_response));
  859. break;
  860. }
  861. return 0;
  862. #endif
  863. pr_info("In the socket_thread_function function");
  864. return 0;
  865. }
  866. EXPORT_SYMBOL(socket_thread_function);