1 /* 2 * Copyright (c) 2015-2016 Dmitry V. Levin <ldv (at) altlinux.org> 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. The name of the author may not be used to endorse or promote products 14 * derived from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 21 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 25 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 */ 27 28 #include "defs.h" 29 30 #include DEF_MPERS_TYPE(timespec_t) 31 32 typedef struct timespec timespec_t; 33 34 #include MPERS_DEFS 35 36 #ifndef UTIME_NOW 37 # define UTIME_NOW ((1l << 30) - 1l) 38 #endif 39 #ifndef UTIME_OMIT 40 # define UTIME_OMIT ((1l << 30) - 2l) 41 #endif 42 43 static const char timespec_fmt[] = "{tv_sec=%jd, tv_nsec=%jd}"; 44 45 static void 46 print_timespec_t(const timespec_t *t) 47 { 48 tprintf(timespec_fmt, (intmax_t) t->tv_sec, (intmax_t) t->tv_nsec); 49 } 50 51 static void 52 print_timespec_t_utime(const timespec_t *t) 53 { 54 switch (t->tv_nsec) { 55 case UTIME_NOW: 56 tprints("UTIME_NOW"); 57 break; 58 case UTIME_OMIT: 59 tprints("UTIME_OMIT"); 60 break; 61 default: 62 print_timespec_t(t); 63 break; 64 } 65 } 66 67 MPERS_PRINTER_DECL(void, print_timespec, 68 struct tcb *const tcp, const kernel_ulong_t addr) 69 { 70 timespec_t t; 71 72 if (umove_or_printaddr(tcp, addr, &t)) 73 return; 74 75 print_timespec_t(&t); 76 } 77 78 MPERS_PRINTER_DECL(const char *, sprint_timespec, 79 struct tcb *const tcp, const kernel_ulong_t addr) 80 { 81 timespec_t t; 82 static char buf[sizeof(timespec_fmt) + 3 * sizeof(t)]; 83 84 if (!addr) { 85 strcpy(buf, "NULL"); 86 } else if (!verbose(tcp) || (exiting(tcp) && syserror(tcp)) || 87 umove(tcp, addr, &t)) { 88 snprintf(buf, sizeof(buf), "%#" PRI_klx, addr); 89 } else { 90 snprintf(buf, sizeof(buf), timespec_fmt, 91 (intmax_t) t.tv_sec, (intmax_t) t.tv_nsec); 92 } 93 94 return buf; 95 } 96 97 MPERS_PRINTER_DECL(void, print_timespec_utime_pair, 98 struct tcb *const tcp, const kernel_ulong_t addr) 99 { 100 timespec_t t[2]; 101 102 if (umove_or_printaddr(tcp, addr, &t)) 103 return; 104 105 tprints("["); 106 print_timespec_t_utime(&t[0]); 107 tprints(", "); 108 print_timespec_t_utime(&t[1]); 109 tprints("]"); 110 } 111 112 MPERS_PRINTER_DECL(void, print_itimerspec, 113 struct tcb *const tcp, const kernel_ulong_t addr) 114 { 115 timespec_t t[2]; 116 117 if (umove_or_printaddr(tcp, addr, &t)) 118 return; 119 120 tprints("{it_interval="); 121 print_timespec_t(&t[0]); 122 tprints(", it_value="); 123 print_timespec_t(&t[1]); 124 tprints("}"); 125 } 126