| 1 | //===-- sanitizer_platform_limits_solaris.h -------------------------------===// |
| 2 | // |
| 3 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. |
| 4 | // See https://llvm.org/LICENSE.txt for license information. |
| 5 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception |
| 6 | // |
| 7 | //===----------------------------------------------------------------------===// |
| 8 | // |
| 9 | // This file is a part of Sanitizer common code. |
| 10 | // |
| 11 | // Sizes and layouts of platform-specific Solaris data structures. |
| 12 | //===----------------------------------------------------------------------===// |
| 13 | |
| 14 | #ifndef SANITIZER_PLATFORM_LIMITS_SOLARIS_H |
| 15 | #define SANITIZER_PLATFORM_LIMITS_SOLARIS_H |
| 16 | |
| 17 | #if SANITIZER_SOLARIS |
| 18 | |
| 19 | #include "sanitizer_internal_defs.h" |
| 20 | #include "sanitizer_platform.h" |
| 21 | |
| 22 | namespace __sanitizer { |
| 23 | extern unsigned struct_utsname_sz; |
| 24 | extern unsigned struct_stat_sz; |
| 25 | extern unsigned struct_stat64_sz; |
| 26 | extern unsigned struct_rusage_sz; |
| 27 | extern unsigned siginfo_t_sz; |
| 28 | extern unsigned struct_itimerval_sz; |
| 29 | extern unsigned pthread_t_sz; |
| 30 | extern unsigned pthread_mutex_t_sz; |
| 31 | extern unsigned pthread_cond_t_sz; |
| 32 | extern unsigned pid_t_sz; |
| 33 | extern unsigned timeval_sz; |
| 34 | extern unsigned uid_t_sz; |
| 35 | extern unsigned gid_t_sz; |
| 36 | extern unsigned mbstate_t_sz; |
| 37 | extern unsigned struct_timezone_sz; |
| 38 | extern unsigned struct_tms_sz; |
| 39 | extern unsigned struct_itimerspec_sz; |
| 40 | extern unsigned struct_sigevent_sz; |
| 41 | extern unsigned struct_stack_t_sz; |
| 42 | extern unsigned struct_sched_param_sz; |
| 43 | extern unsigned struct_statfs64_sz; |
| 44 | extern unsigned struct_statfs_sz; |
| 45 | extern unsigned struct_sockaddr_sz; |
| 46 | unsigned ucontext_t_sz(void *ctx); |
| 47 | |
| 48 | extern unsigned struct_timespec_sz; |
| 49 | extern unsigned struct_rlimit_sz; |
| 50 | extern unsigned struct_utimbuf_sz; |
| 51 | |
| 52 | struct __sanitizer_sem_t { |
| 53 | //u64 data[6]; |
| 54 | u32 sem_count; |
| 55 | u16 sem_type; |
| 56 | u16 sem_magic; |
| 57 | u64 sem_pad1[3]; |
| 58 | u64 sem_pad2[2]; |
| 59 | }; |
| 60 | |
| 61 | struct __sanitizer_ipc_perm { |
| 62 | unsigned int uid; // uid_t |
| 63 | unsigned int gid; // gid_t |
| 64 | unsigned int cuid; // uid_t |
| 65 | unsigned int cgid; // gid_t |
| 66 | unsigned int mode; // mode_t |
| 67 | unsigned int seq; // uint_t |
| 68 | int key; // key_t |
| 69 | #if !defined(_LP64) |
| 70 | int pad[4]; |
| 71 | #endif |
| 72 | }; |
| 73 | |
| 74 | struct __sanitizer_shmid_ds { |
| 75 | __sanitizer_ipc_perm shm_perm; |
| 76 | unsigned long shm_segsz; // size_t |
| 77 | unsigned long shm_flags; // uintptr_t |
| 78 | unsigned short shm_lkcnt; // ushort_t |
| 79 | int shm_lpid; // pid_t |
| 80 | int shm_cpid; // pid_t |
| 81 | unsigned long shm_nattch; // shmatt_t |
| 82 | unsigned long shm_cnattch; // ulong_t |
| 83 | #if defined(_LP64) |
| 84 | long shm_atime; // time_t |
| 85 | long shm_dtime; |
| 86 | long shm_ctime; |
| 87 | void *shm_amp; |
| 88 | u64 shm_gransize; // uint64_t |
| 89 | u64 shm_allocated; // uint64_t |
| 90 | u64 shm_pad4[1]; // int64_t |
| 91 | #else |
| 92 | long shm_atime; // time_t |
| 93 | int shm_pad1; // int32_t |
| 94 | long shm_dtime; // time_t |
| 95 | int shm_pad2; // int32_t |
| 96 | long shm_ctime; // time_t |
| 97 | void *shm_amp; |
| 98 | u64 shm_gransize; // uint64_t |
| 99 | u64 shm_allocated; // uint64_t |
| 100 | #endif |
| 101 | }; |
| 102 | |
| 103 | extern unsigned struct_statvfs_sz; |
| 104 | #if SANITIZER_SOLARIS32 |
| 105 | extern unsigned struct_statvfs64_sz; |
| 106 | #endif |
| 107 | |
| 108 | struct __sanitizer_iovec { |
| 109 | void *iov_base; |
| 110 | uptr iov_len; |
| 111 | }; |
| 112 | |
| 113 | struct __sanitizer_ifaddrs { |
| 114 | struct __sanitizer_ifaddrs *ifa_next; |
| 115 | char *ifa_name; |
| 116 | u64 ifa_flags; // uint64_t |
| 117 | void *ifa_addr; // (struct sockaddr *) |
| 118 | void *ifa_netmask; // (struct sockaddr *) |
| 119 | // This is a union on Linux. |
| 120 | # ifdef ifa_dstaddr |
| 121 | # undef ifa_dstaddr |
| 122 | # endif |
| 123 | void *ifa_dstaddr; // (struct sockaddr *) |
| 124 | void *ifa_data; |
| 125 | }; |
| 126 | |
| 127 | typedef unsigned __sanitizer_pthread_key_t; |
| 128 | |
| 129 | struct __sanitizer_XDR { |
| 130 | int x_op; |
| 131 | void *x_ops; |
| 132 | uptr x_public; |
| 133 | uptr x_private; |
| 134 | uptr x_base; |
| 135 | unsigned x_handy; |
| 136 | }; |
| 137 | |
| 138 | const int __sanitizer_XDR_ENCODE = 0; |
| 139 | const int __sanitizer_XDR_DECODE = 1; |
| 140 | const int __sanitizer_XDR_FREE = 2; |
| 141 | |
| 142 | struct __sanitizer_passwd { |
| 143 | char *pw_name; |
| 144 | char *pw_passwd; |
| 145 | unsigned int pw_uid; // uid_t |
| 146 | unsigned int pw_gid; // gid_t |
| 147 | char *pw_age; |
| 148 | char *pw_comment; |
| 149 | char *pw_gecos; |
| 150 | char *pw_dir; |
| 151 | char *pw_shell; |
| 152 | }; |
| 153 | |
| 154 | struct __sanitizer_group { |
| 155 | char *gr_name; |
| 156 | char *gr_passwd; |
| 157 | int gr_gid; |
| 158 | char **gr_mem; |
| 159 | }; |
| 160 | |
| 161 | typedef long __sanitizer_time_t; |
| 162 | |
| 163 | typedef long __sanitizer_suseconds_t; |
| 164 | |
| 165 | struct __sanitizer_timeval { |
| 166 | __sanitizer_time_t tv_sec; |
| 167 | __sanitizer_suseconds_t tv_usec; |
| 168 | }; |
| 169 | |
| 170 | struct __sanitizer_itimerval { |
| 171 | struct __sanitizer_timeval it_interval; |
| 172 | struct __sanitizer_timeval it_value; |
| 173 | }; |
| 174 | |
| 175 | struct __sanitizer_timeb { |
| 176 | __sanitizer_time_t time; |
| 177 | unsigned short millitm; |
| 178 | short timezone; |
| 179 | short dstflag; |
| 180 | }; |
| 181 | |
| 182 | struct __sanitizer_ether_addr { |
| 183 | u8 octet[6]; |
| 184 | }; |
| 185 | |
| 186 | struct __sanitizer_tm { |
| 187 | int tm_sec; |
| 188 | int tm_min; |
| 189 | int tm_hour; |
| 190 | int tm_mday; |
| 191 | int tm_mon; |
| 192 | int tm_year; |
| 193 | int tm_wday; |
| 194 | int tm_yday; |
| 195 | int tm_isdst; |
| 196 | }; |
| 197 | |
| 198 | struct __sanitizer_msghdr { |
| 199 | void *msg_name; |
| 200 | unsigned msg_namelen; |
| 201 | struct __sanitizer_iovec *msg_iov; |
| 202 | unsigned msg_iovlen; |
| 203 | void *msg_control; |
| 204 | unsigned msg_controllen; |
| 205 | int msg_flags; |
| 206 | }; |
| 207 | struct __sanitizer_cmsghdr { |
| 208 | unsigned cmsg_len; |
| 209 | int cmsg_level; |
| 210 | int cmsg_type; |
| 211 | }; |
| 212 | |
| 213 | #if SANITIZER_SOLARIS && (defined(_LP64) || _FILE_OFFSET_BITS == 64) |
| 214 | struct __sanitizer_dirent { |
| 215 | unsigned long long d_ino; |
| 216 | long long d_off; |
| 217 | unsigned short d_reclen; |
| 218 | // more fields that we don't care about |
| 219 | }; |
| 220 | #else |
| 221 | struct __sanitizer_dirent { |
| 222 | unsigned long d_ino; |
| 223 | long d_off; |
| 224 | unsigned short d_reclen; |
| 225 | // more fields that we don't care about |
| 226 | }; |
| 227 | #endif |
| 228 | |
| 229 | struct __sanitizer_dirent64 { |
| 230 | unsigned long long d_ino; |
| 231 | unsigned long long d_off; |
| 232 | unsigned short d_reclen; |
| 233 | // more fields that we don't care about |
| 234 | }; |
| 235 | |
| 236 | typedef long __sanitizer_clock_t; |
| 237 | typedef int __sanitizer_clockid_t; |
| 238 | |
| 239 | // This thing depends on the platform. We are only interested in the upper |
| 240 | // limit. Verified with a compiler assert in .cpp. |
| 241 | union __sanitizer_pthread_attr_t { |
| 242 | char size[128]; |
| 243 | void *align; |
| 244 | }; |
| 245 | |
| 246 | struct __sanitizer_sigset_t { |
| 247 | // uint32_t * 4 |
| 248 | unsigned int __bits[4]; |
| 249 | }; |
| 250 | |
| 251 | struct __sanitizer_siginfo { |
| 252 | // The size is determined by looking at sizeof of real siginfo_t on linux. |
| 253 | u64 opaque[128 / sizeof(u64)]; |
| 254 | }; |
| 255 | |
| 256 | using __sanitizer_sighandler_ptr = void (*)(int sig); |
| 257 | using __sanitizer_sigactionhandler_ptr = |
| 258 | void (*)(int sig, __sanitizer_siginfo *siginfo, void *uctx); |
| 259 | |
| 260 | struct __sanitizer_sigaction { |
| 261 | int sa_flags; |
| 262 | union { |
| 263 | __sanitizer_sigactionhandler_ptr sigaction; |
| 264 | __sanitizer_sighandler_ptr handler; |
| 265 | }; |
| 266 | __sanitizer_sigset_t sa_mask; |
| 267 | #if !defined(_LP64) |
| 268 | int sa_resv[2]; |
| 269 | #endif |
| 270 | }; |
| 271 | |
| 272 | struct __sanitizer_kernel_sigset_t { |
| 273 | u8 sig[8]; |
| 274 | }; |
| 275 | |
| 276 | struct __sanitizer_kernel_sigaction_t { |
| 277 | union { |
| 278 | void (*handler)(int signo); |
| 279 | void (*sigaction)(int signo, __sanitizer_siginfo *info, void *ctx); |
| 280 | }; |
| 281 | unsigned long sa_flags; |
| 282 | void (*sa_restorer)(void); |
| 283 | __sanitizer_kernel_sigset_t sa_mask; |
| 284 | }; |
| 285 | |
| 286 | extern const uptr sig_ign; |
| 287 | extern const uptr sig_dfl; |
| 288 | extern const uptr sig_err; |
| 289 | extern const uptr sa_siginfo; |
| 290 | |
| 291 | extern int af_inet; |
| 292 | extern int af_inet6; |
| 293 | uptr __sanitizer_in_addr_sz(int af); |
| 294 | |
| 295 | struct __sanitizer_dl_phdr_info { |
| 296 | uptr dlpi_addr; |
| 297 | const char *dlpi_name; |
| 298 | const void *dlpi_phdr; |
| 299 | short dlpi_phnum; |
| 300 | }; |
| 301 | |
| 302 | extern unsigned struct_ElfW_Phdr_sz; |
| 303 | |
| 304 | struct __sanitizer_addrinfo { |
| 305 | int ai_flags; |
| 306 | int ai_family; |
| 307 | int ai_socktype; |
| 308 | int ai_protocol; |
| 309 | #if defined(__sparcv9) |
| 310 | int _ai_pad; |
| 311 | #endif |
| 312 | unsigned ai_addrlen; |
| 313 | char *ai_canonname; |
| 314 | void *ai_addr; |
| 315 | struct __sanitizer_addrinfo *ai_next; |
| 316 | }; |
| 317 | |
| 318 | struct __sanitizer_hostent { |
| 319 | char *h_name; |
| 320 | char **h_aliases; |
| 321 | int h_addrtype; |
| 322 | int h_length; |
| 323 | char **h_addr_list; |
| 324 | }; |
| 325 | |
| 326 | struct __sanitizer_pollfd { |
| 327 | int fd; |
| 328 | short events; |
| 329 | short revents; |
| 330 | }; |
| 331 | |
| 332 | typedef unsigned long __sanitizer_nfds_t; |
| 333 | |
| 334 | struct __sanitizer_glob_t { |
| 335 | uptr gl_pathc; |
| 336 | char **gl_pathv; |
| 337 | uptr gl_offs; |
| 338 | char **gl_pathp; |
| 339 | int gl_pathn; |
| 340 | }; |
| 341 | |
| 342 | extern int glob_nomatch; |
| 343 | extern int glob_altdirfunc; |
| 344 | extern const int wordexp_wrde_dooffs; |
| 345 | |
| 346 | extern unsigned path_max; |
| 347 | |
| 348 | struct __sanitizer_wordexp_t { |
| 349 | uptr we_wordc; |
| 350 | char **we_wordv; |
| 351 | uptr we_offs; |
| 352 | char **we_wordp; |
| 353 | int we_wordn; |
| 354 | }; |
| 355 | |
| 356 | typedef void __sanitizer_FILE; |
| 357 | #define SANITIZER_HAS_STRUCT_FILE 0 |
| 358 | |
| 359 | // This simplifies generic code |
| 360 | #define struct_shminfo_sz -1 |
| 361 | #define struct_shm_info_sz -1 |
| 362 | #define shmctl_shm_stat -1 |
| 363 | #define shmctl_ipc_info -1 |
| 364 | #define shmctl_shm_info -1 |
| 365 | |
| 366 | extern int shmctl_ipc_stat; |
| 367 | |
| 368 | extern unsigned struct_utmp_sz; |
| 369 | extern unsigned struct_utmpx_sz; |
| 370 | |
| 371 | extern int map_fixed; |
| 372 | |
| 373 | // ioctl arguments |
| 374 | struct __sanitizer_ifconf { |
| 375 | int ifc_len; |
| 376 | union { |
| 377 | void *ifcu_req; |
| 378 | } ifc_ifcu; |
| 379 | }; |
| 380 | |
| 381 | // <sys/ioccom.h> |
| 382 | #define IOC_NRBITS 8 |
| 383 | #define IOC_TYPEBITS 8 |
| 384 | #define IOC_SIZEBITS 12 |
| 385 | #define IOC_DIRBITS 4 |
| 386 | #undef IOC_NONE |
| 387 | #define IOC_NONE 2U // IOC_VOID |
| 388 | #define IOC_READ 4U // IOC_OUT |
| 389 | #define IOC_WRITE 8U // IOC_IN |
| 390 | |
| 391 | #define IOC_NRMASK ((1 << IOC_NRBITS) - 1) |
| 392 | #define IOC_TYPEMASK ((1 << IOC_TYPEBITS) - 1) |
| 393 | #define IOC_SIZEMASK ((1 << IOC_SIZEBITS) - 1) |
| 394 | #define IOC_DIRMASK ((1 << IOC_DIRBITS) - 1) |
| 395 | #define IOC_NRSHIFT 0 |
| 396 | #define IOC_TYPESHIFT (IOC_NRSHIFT + IOC_NRBITS) |
| 397 | #define IOC_SIZESHIFT (IOC_TYPESHIFT + IOC_TYPEBITS) |
| 398 | #define IOC_DIRSHIFT (IOC_SIZESHIFT + IOC_SIZEBITS) |
| 399 | |
| 400 | #define IOC_DIR(nr) (((nr) >> IOC_DIRSHIFT) & IOC_DIRMASK) |
| 401 | #define IOC_TYPE(nr) (((nr) >> IOC_TYPESHIFT) & IOC_TYPEMASK) |
| 402 | #define IOC_NR(nr) (((nr) >> IOC_NRSHIFT) & IOC_NRMASK) |
| 403 | |
| 404 | #if defined(__sparc__) |
| 405 | // In sparc the 14 bits SIZE field overlaps with the |
| 406 | // least significant bit of DIR, so either IOC_READ or |
| 407 | // IOC_WRITE shall be 1 in order to get a non-zero SIZE. |
| 408 | #define IOC_SIZE(nr) \ |
| 409 | ((((((nr) >> 29) & 0x7) & (4U | 2U)) == 0) ? 0 : (((nr) >> 16) & 0x3fff)) |
| 410 | #else |
| 411 | #define IOC_SIZE(nr) (((nr) >> IOC_SIZESHIFT) & IOC_SIZEMASK) |
| 412 | #endif |
| 413 | |
| 414 | extern unsigned struct_ifreq_sz; |
| 415 | extern unsigned struct_termios_sz; |
| 416 | extern unsigned struct_winsize_sz; |
| 417 | |
| 418 | extern unsigned struct_sioc_sg_req_sz; |
| 419 | extern unsigned struct_sioc_vif_req_sz; |
| 420 | |
| 421 | extern unsigned fpos_t_sz; |
| 422 | |
| 423 | // ioctl request identifiers |
| 424 | |
| 425 | // A special value to mark ioctls that are not present on the target platform, |
| 426 | // when it can not be determined without including any system headers. |
| 427 | extern const unsigned IOCTL_NOT_PRESENT; |
| 428 | |
| 429 | extern unsigned IOCTL_FIOASYNC; |
| 430 | extern unsigned IOCTL_FIOCLEX; |
| 431 | extern unsigned IOCTL_FIOGETOWN; |
| 432 | extern unsigned IOCTL_FIONBIO; |
| 433 | extern unsigned IOCTL_FIONCLEX; |
| 434 | extern unsigned IOCTL_FIOSETOWN; |
| 435 | extern unsigned IOCTL_SIOCADDMULTI; |
| 436 | extern unsigned IOCTL_SIOCATMARK; |
| 437 | extern unsigned IOCTL_SIOCDELMULTI; |
| 438 | extern unsigned IOCTL_SIOCGIFADDR; |
| 439 | extern unsigned IOCTL_SIOCGIFBRDADDR; |
| 440 | extern unsigned IOCTL_SIOCGIFCONF; |
| 441 | extern unsigned IOCTL_SIOCGIFDSTADDR; |
| 442 | extern unsigned IOCTL_SIOCGIFFLAGS; |
| 443 | extern unsigned IOCTL_SIOCGIFMETRIC; |
| 444 | extern unsigned IOCTL_SIOCGIFMTU; |
| 445 | extern unsigned IOCTL_SIOCGIFNETMASK; |
| 446 | extern unsigned IOCTL_SIOCGPGRP; |
| 447 | extern unsigned IOCTL_SIOCSIFADDR; |
| 448 | extern unsigned IOCTL_SIOCSIFBRDADDR; |
| 449 | extern unsigned IOCTL_SIOCSIFDSTADDR; |
| 450 | extern unsigned IOCTL_SIOCSIFFLAGS; |
| 451 | extern unsigned IOCTL_SIOCSIFMETRIC; |
| 452 | extern unsigned IOCTL_SIOCSIFMTU; |
| 453 | extern unsigned IOCTL_SIOCSIFNETMASK; |
| 454 | extern unsigned IOCTL_SIOCSPGRP; |
| 455 | extern unsigned IOCTL_TIOCEXCL; |
| 456 | extern unsigned IOCTL_TIOCGETD; |
| 457 | extern unsigned IOCTL_TIOCGPGRP; |
| 458 | extern unsigned IOCTL_TIOCGWINSZ; |
| 459 | extern unsigned IOCTL_TIOCMBIC; |
| 460 | extern unsigned IOCTL_TIOCMBIS; |
| 461 | extern unsigned IOCTL_TIOCMGET; |
| 462 | extern unsigned IOCTL_TIOCMSET; |
| 463 | extern unsigned IOCTL_TIOCNOTTY; |
| 464 | extern unsigned IOCTL_TIOCNXCL; |
| 465 | extern unsigned IOCTL_TIOCOUTQ; |
| 466 | extern unsigned IOCTL_TIOCPKT; |
| 467 | extern unsigned IOCTL_TIOCSCTTY; |
| 468 | extern unsigned IOCTL_TIOCSETD; |
| 469 | extern unsigned IOCTL_TIOCSPGRP; |
| 470 | extern unsigned IOCTL_TIOCSTI; |
| 471 | extern unsigned IOCTL_TIOCSWINSZ; |
| 472 | extern unsigned IOCTL_MTIOCGET; |
| 473 | extern unsigned IOCTL_MTIOCTOP; |
| 474 | |
| 475 | extern const int si_SEGV_MAPERR; |
| 476 | extern const int si_SEGV_ACCERR; |
| 477 | } // namespace __sanitizer |
| 478 | |
| 479 | #define CHECK_TYPE_SIZE(TYPE) \ |
| 480 | COMPILER_CHECK(sizeof(__sanitizer_##TYPE) == sizeof(TYPE)) |
| 481 | |
| 482 | #define CHECK_SIZE_AND_OFFSET(CLASS, MEMBER) \ |
| 483 | COMPILER_CHECK(sizeof(((__sanitizer_##CLASS *) NULL)->MEMBER) == \ |
| 484 | sizeof(((CLASS *) NULL)->MEMBER)); \ |
| 485 | COMPILER_CHECK(offsetof(__sanitizer_##CLASS, MEMBER) == \ |
| 486 | offsetof(CLASS, MEMBER)) |
| 487 | |
| 488 | // For sigaction, which is a function and struct at the same time, |
| 489 | // and thus requires explicit "struct" in sizeof() expression. |
| 490 | #define CHECK_STRUCT_SIZE_AND_OFFSET(CLASS, MEMBER) \ |
| 491 | COMPILER_CHECK(sizeof(((struct __sanitizer_##CLASS *) NULL)->MEMBER) == \ |
| 492 | sizeof(((struct CLASS *) NULL)->MEMBER)); \ |
| 493 | COMPILER_CHECK(offsetof(struct __sanitizer_##CLASS, MEMBER) == \ |
| 494 | offsetof(struct CLASS, MEMBER)) |
| 495 | |
| 496 | #endif // SANITIZER_SOLARIS |
| 497 | |
| 498 | #endif |
| 499 | |