1 /* $NetBSD: linux32_socket.c,v 1.4 2007/12/08 18:36:12 dsl Exp $ */ 2 3 /*- 4 * Copyright (c) 2006 Emmanuel Dreyfus, all rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 3. All advertising materials mentioning features or use of this software 15 * must display the following acknowledgement: 16 * This product includes software developed by Emmanuel Dreyfus 17 * 4. The name of the author may not be used to endorse or promote 18 * products derived from this software without specific prior written 19 * permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE THE AUTHOR AND CONTRIBUTORS ``AS IS'' 22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, 23 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 24 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS 25 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 31 * POSSIBILITY OF SUCH DAMAGE. 32 */ 33 34 #include <sys/cdefs.h> 35 36 __KERNEL_RCSID(0, "$NetBSD: linux32_socket.c,v 1.4 2007/12/08 18:36:12 dsl Exp $"); 37 38 #include <sys/types.h> 39 #include <sys/param.h> 40 #include <sys/fstypes.h> 41 #include <sys/signal.h> 42 #include <sys/dirent.h> 43 #include <sys/kernel.h> 44 #include <sys/fcntl.h> 45 #include <sys/select.h> 46 #include <sys/proc.h> 47 #include <sys/ucred.h> 48 #include <sys/swap.h> 49 50 #include <machine/types.h> 51 52 #include <sys/syscallargs.h> 53 54 #include <compat/netbsd32/netbsd32.h> 55 #include <compat/netbsd32/netbsd32_conv.h> 56 #include <compat/netbsd32/netbsd32_syscallargs.h> 57 58 #include <compat/linux/common/linux_types.h> 59 #include <compat/linux/common/linux_signal.h> 60 #include <compat/linux/common/linux_machdep.h> 61 #include <compat/linux/common/linux_misc.h> 62 #include <compat/linux/common/linux_oldolduname.h> 63 #include <compat/linux/linux_syscallargs.h> 64 65 #include <compat/linux32/common/linux32_types.h> 66 #include <compat/linux32/common/linux32_signal.h> 67 #include <compat/linux32/common/linux32_machdep.h> 68 #include <compat/linux32/common/linux32_sysctl.h> 69 #include <compat/linux32/common/linux32_socketcall.h> 70 #include <compat/linux32/linux32_syscallargs.h> 71 72 int 73 linux32_sys_socketpair(struct lwp *l, void *v, register_t *retval) 74 { 75 struct linux32_sys_socketpair_args /* { 76 syscallarg(int) domain; 77 syscallarg(int) type; 78 syscallarg(int) protocol; 79 syscallarg(netbsd32_intp) rsv; 80 } */ *uap = v; 81 struct linux_sys_socketpair_args ua; 82 83 NETBSD32TO64_UAP(domain); 84 NETBSD32TO64_UAP(type); 85 NETBSD32TO64_UAP(protocol); 86 NETBSD32TOP_UAP(rsv, int) 87 88 return linux_sys_socketpair(l, &ua, retval); 89 } 90 91 int 92 linux32_sys_sendto(struct lwp *l, void *v, register_t *retval) 93 { 94 struct linux32_sys_sendto_args /* { 95 syscallarg(int) s; 96 syscallarg(netbsd32_voidp) msg; 97 syscallarg(int) len; 98 syscallarg(int) flags; 99 syscallarg(netbsd32_osockaddrp_t) to; 100 syscallarg(int) tolen; 101 } */ *uap = v; 102 struct linux_sys_sendto_args ua; 103 104 NETBSD32TO64_UAP(s); 105 NETBSD32TOP_UAP(msg, void); 106 NETBSD32TO64_UAP(len); 107 NETBSD32TO64_UAP(flags); 108 NETBSD32TOP_UAP(to, struct osockaddr); 109 NETBSD32TO64_UAP(tolen); 110 111 return linux_sys_sendto(l, &ua, retval); 112 } 113 114 115 int 116 linux32_sys_recvfrom(struct lwp *l, void *v, register_t *retval) 117 { 118 struct linux32_sys_recvfrom_args /* { 119 syscallarg(int) s; 120 syscallarg(netbsd32_voidp) buf; 121 syscallarg(netbsd32_size_t) len; 122 syscallarg(int) flags; 123 syscallarg(netbsd32_osockaddrp_t) from; 124 syscallarg(netbsd32_intp) fromlenaddr; 125 } */ *uap = v; 126 struct linux_sys_recvfrom_args ua; 127 128 NETBSD32TO64_UAP(s); 129 NETBSD32TOP_UAP(buf, void); 130 NETBSD32TO64_UAP(len); 131 NETBSD32TO64_UAP(flags); 132 NETBSD32TOP_UAP(from, struct osockaddr); 133 NETBSD32TOP_UAP(fromlenaddr, unsigned int); 134 135 return linux_sys_recvfrom(l, &ua, retval); 136 } 137 138 int 139 linux32_sys_setsockopt(struct lwp *l, void *v, register_t *retval) 140 { 141 struct linux32_sys_setsockopt_args /* { 142 syscallarg(int) s; 143 syscallarg(int) level; 144 syscallarg(int) optname; 145 syscallarg(netbsd32_voidp) optval; 146 syscallarg(int) optlen; 147 } */ *uap = v; 148 struct linux_sys_setsockopt_args ua; 149 150 NETBSD32TO64_UAP(s); 151 NETBSD32TO64_UAP(level); 152 NETBSD32TO64_UAP(optname); 153 NETBSD32TOP_UAP(optval, void); 154 NETBSD32TO64_UAP(optlen); 155 156 return linux_sys_setsockopt(l, &ua, retval); 157 } 158 159 160 int 161 linux32_sys_getsockopt(struct lwp *l, void *v, register_t *retval) 162 { 163 struct linux32_sys_getsockopt_args /* { 164 syscallarg(int) s; 165 syscallarg(int) level; 166 syscallarg(int) optname; 167 syscallarg(netbsd32_voidp) optval; 168 syscallarg(netbsd32_intp) optlen; 169 } */ *uap = v; 170 struct linux_sys_getsockopt_args ua; 171 172 NETBSD32TO64_UAP(s); 173 NETBSD32TO64_UAP(level); 174 NETBSD32TO64_UAP(optname); 175 NETBSD32TOP_UAP(optval, void); 176 NETBSD32TOP_UAP(optlen, int); 177 178 return linux_sys_getsockopt(l, &ua, retval); 179 } 180 181 int 182 linux32_sys_socket(struct lwp *l, void *v, register_t *retval) 183 { 184 struct linux32_sys_socket_args /* { 185 syscallarg(int) domain; 186 syscallarg(int) type; 187 syscallarg(int) protocol; 188 } */ *uap = v; 189 struct linux_sys_socket_args ua; 190 191 NETBSD32TO64_UAP(domain); 192 NETBSD32TO64_UAP(type); 193 NETBSD32TO64_UAP(protocol); 194 195 return linux_sys_socket(l, &ua, retval); 196 } 197 198 int 199 linux32_sys_bind(struct lwp *l, void *v, register_t *retval) 200 { 201 struct linux32_sys_bind_args /* { 202 syscallarg(int) s; 203 syscallarg(netbsd32_osockaddrp_t) name; 204 syscallarg(int) namelen; 205 } */ *uap = v; 206 struct linux_sys_bind_args ua; 207 208 NETBSD32TO64_UAP(s); 209 NETBSD32TOP_UAP(name, struct osockaddr) 210 NETBSD32TO64_UAP(namelen); 211 212 return linux_sys_bind(l, &ua, retval); 213 } 214 215 int 216 linux32_sys_connect(struct lwp *l, void *v, register_t *retval) 217 { 218 struct linux32_sys_connect_args /* { 219 syscallarg(int) s; 220 syscallarg(netbsd32_osockaddrp_t) name; 221 syscallarg(int) namelen; 222 } */ *uap = v; 223 struct linux_sys_connect_args ua; 224 225 NETBSD32TO64_UAP(s); 226 NETBSD32TOP_UAP(name, struct osockaddr) 227 NETBSD32TO64_UAP(namelen); 228 229 #ifdef DEBUG_LINUX 230 printf("linux32_sys_connect: s = %d, name = %p, namelen = %d\n", 231 SCARG(&ua, s), SCARG(&ua, name), SCARG(&ua, namelen)); 232 #endif 233 234 return linux_sys_connect(l, &ua, retval); 235 } 236 237 int 238 linux32_sys_accept(struct lwp *l, void *v, register_t *retval) 239 { 240 struct linux32_sys_accept_args /* { 241 syscallarg(int) s; 242 syscallarg(netbsd32_osockaddrp_t) name; 243 syscallarg(netbsd32_intp) anamelen; 244 } */ *uap = v; 245 struct linux_sys_accept_args ua; 246 247 NETBSD32TO64_UAP(s); 248 NETBSD32TOP_UAP(name, struct osockaddr) 249 NETBSD32TOP_UAP(anamelen, int); 250 251 return linux_sys_accept(l, &ua, retval); 252 } 253 254 int 255 linux32_sys_getpeername(struct lwp *l, void *v, register_t *retval) 256 { 257 struct linux32_sys_getpeername_args /* { 258 syscallarg(int) fdes; 259 syscallarg(netbsd32_sockaddrp_t) asa; 260 syscallarg(netbsd32_intp) alen; 261 } */ *uap = v; 262 struct linux_sys_getpeername_args ua; 263 264 NETBSD32TO64_UAP(fdes); 265 NETBSD32TOP_UAP(asa, struct sockaddr) 266 NETBSD32TOP_UAP(alen, int); 267 268 return linux_sys_getpeername(l, &ua, retval); 269 } 270 271 int 272 linux32_sys_getsockname(struct lwp *l, void *v, register_t *retval) 273 { 274 struct linux32_sys_getsockname_args /* { 275 syscallarg(int) fdec; 276 syscallarg(netbsd32_charp) asa; 277 syscallarg(netbsd32_intp) alen; 278 } */ *uap = v; 279 struct linux_sys_getsockname_args ua; 280 281 NETBSD32TO64_UAP(fdec); 282 NETBSD32TOP_UAP(asa, char) 283 NETBSD32TOP_UAP(alen, int); 284 285 return linux_sys_getsockname(l, &ua, retval); 286 } 287 288 int 289 linux32_sys_sendmsg(struct lwp *l, void *v, register_t *retval) 290 { 291 struct linux32_sys_sendmsg_args /* { 292 syscallarg(int) s; 293 syscallarg(netbsd32_msghdrp_t) msg; 294 syscallarg(int) flags; 295 } */ *uap = v; 296 struct linux_sys_sendmsg_args ua; 297 298 NETBSD32TO64_UAP(s); 299 NETBSD32TOP_UAP(msg, struct msghdr); 300 NETBSD32TO64_UAP(flags); 301 302 return linux_sys_sendmsg(l, &ua, retval); 303 } 304 305 int 306 linux32_sys_recvmsg(struct lwp *l, void *v, register_t *retval) 307 { 308 struct linux32_sys_recvmsg_args /* { 309 syscallarg(int) s; 310 syscallarg(netbsd32_msghdrp_t) msg; 311 syscallarg(int) flags; 312 } */ *uap = v; 313 struct linux_sys_recvmsg_args ua; 314 315 NETBSD32TO64_UAP(s); 316 NETBSD32TOP_UAP(msg, struct msghdr); 317 NETBSD32TO64_UAP(flags); 318 319 return linux_sys_recvmsg(l, &ua, retval); 320 } 321 322 int 323 linux32_sys_send(struct lwp *l, void *v, register_t *retval) 324 { 325 struct linux32_sys_send_args /* { 326 syscallarg(int) s; 327 syscallarg(netbsd32_voidp) buf; 328 syscallarg(int) len; 329 syscallarg(int) flags; 330 } */ *uap = v; 331 struct sys_sendto_args ua; 332 333 NETBSD32TO64_UAP(s); 334 NETBSD32TOP_UAP(buf, void); 335 NETBSD32TO64_UAP(len); 336 NETBSD32TO64_UAP(flags); 337 SCARG(&ua, to) = NULL; 338 SCARG(&ua, tolen) = 0; 339 340 return sys_sendto(l, &ua, retval); 341 } 342 343 int 344 linux32_sys_recv(struct lwp *l, void *v, register_t *retval) 345 { 346 struct linux32_sys_recv_args /* { 347 syscallarg(int) s; 348 syscallarg(netbsd32_voidp) buf; 349 syscallarg(int) len; 350 syscallarg(int) flags; 351 } */ *uap = v; 352 struct sys_recvfrom_args ua; 353 354 NETBSD32TO64_UAP(s); 355 NETBSD32TOP_UAP(buf, void); 356 NETBSD32TO64_UAP(len); 357 NETBSD32TO64_UAP(flags); 358 SCARG(&ua, from) = NULL; 359 SCARG(&ua, fromlenaddr) = NULL; 360 361 return sys_recvfrom(l, &ua, retval); 362 } 363