107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*--------------------------------------------------------------------*/
307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*--- Obtaining information about an address.                      ---*/
407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*---                                                 m_addrinfo.c ---*/
507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*--------------------------------------------------------------------*/
607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*
807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   This file is part of Valgrind, a dynamic binary instrumentation
907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   framework.
1007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
11ed39800a83baf5bffbe391f3974eb2af0f415f80Elliott Hughes   Copyright (C) 2008-2017 OpenWorks Ltd
1207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      info@open-works.co.uk
1307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
1407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   This program is free software; you can redistribute it and/or
1507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   modify it under the terms of the GNU General Public License as
1607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   published by the Free Software Foundation; either version 2 of the
1707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   License, or (at your option) any later version.
1807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
1907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   This program is distributed in the hope that it will be useful, but
2007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   WITHOUT ANY WARRANTY; without even the implied warranty of
2107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
2207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   General Public License for more details.
2307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
2407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   You should have received a copy of the GNU General Public License
2507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   along with this program; if not, write to the Free Software
2607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
2707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   02111-1307, USA.
2807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
2907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   The GNU General Public License is contained in the file COPYING.
3007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe*/
3107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
3207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_basics.h"
33d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe#include "pub_core_clientstate.h"
3407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_libcassert.h"
3507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_libcbase.h"
3607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_libcprint.h"
3707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_xarray.h"
3807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_debuginfo.h"
3907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_execontext.h"
4007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_addrinfo.h"
4107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_mallocfree.h"
4207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_machine.h"
4307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe#include "pub_core_options.h"
447e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe#include "pub_core_threadstate.h"
4518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe#include "pub_core_stacktrace.h"
467e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe#include "pub_core_stacks.h"
477e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe#include "pub_core_aspacemgr.h"
487e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
497e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe/* Returns the tid whose stack includes the address a.
507e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   If not found, returns VG_INVALID_THREADID. */
517e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippestatic ThreadId find_tid_with_stack_containing (Addr a)
527e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe{
537e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   ThreadId tid;
547e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   Addr start, end;
557e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
567e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   start = 0;
577e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   end = 0;
587e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   VG_(stack_limits)(a, &start, &end);
597e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   if (start == end) {
607e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      // No stack found
617e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      vg_assert (start == 0 && end == 0);
627e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      return VG_INVALID_THREADID;
637e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   }
647e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
657e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   /* Stack limits found. Search the tid to which this stack belongs. */
667e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   vg_assert (start <= a);
677e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   vg_assert (a <= end);
687e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
697e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   /* The stack end (highest accessible byte) is for sure inside the 'active'
707e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      part of the stack of the searched tid.
717e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      So, scan all 'active' stacks with VG_(thread_stack_reset_iter) ... */
727e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   {
737e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      Addr       stack_min, stack_max;
747e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
757e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      VG_(thread_stack_reset_iter)(&tid);
767e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      while ( VG_(thread_stack_next)(&tid, &stack_min, &stack_max) ) {
777e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         if (stack_min <= end && end <= stack_max)
787e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            return tid;
797e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      }
807e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   }
817e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
827e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   /* We can arrive here if a stack was registered with wrong bounds
837e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      (e.g. end above the highest addressable byte)
847e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      and/or if the thread for the registered stack is dead, but
857e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      the stack was not unregistered. */
867e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   return VG_INVALID_THREADID;
877e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe}
8807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
8907c08527f05caeb0062b42ca9a58ee774ec5fba1philippevoid VG_(describe_addr) ( Addr a, /*OUT*/AddrInfo* ai )
9007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe{
9107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   VgSectKind sect;
9207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
9307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* -- Perhaps the variable type/location data describes it? -- */
9407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   ai->Addr.Variable.descr1
9507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      = VG_(newXA)( VG_(malloc), "mc.da.descr1",
9607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    VG_(free), sizeof(HChar) );
9707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   ai->Addr.Variable.descr2
9807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      = VG_(newXA)( VG_(malloc), "mc.da.descr2",
9907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    VG_(free), sizeof(HChar) );
10007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
10107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   (void) VG_(get_data_description)( ai->Addr.Variable.descr1,
10207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                                     ai->Addr.Variable.descr2, a );
103ad4e979f408239dabbaae955d8ffcb84a51a5c85florian   /* If there's nothing in descr1/2, free them.  Why is it safe to
10407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      VG_(indexXA) at zero here?  Because VG_(get_data_description)
10507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      guarantees to zero terminate descr1/2 regardless of the outcome
10607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      of the call.  So there's always at least one element in each XA
10707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      after the call.
10807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   */
10907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   if (0 == VG_(strlen)( VG_(indexXA)( ai->Addr.Variable.descr1, 0 ))) {
11007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      VG_(deleteXA)( ai->Addr.Variable.descr1 );
11107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      ai->Addr.Variable.descr1 = NULL;
11207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
11307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   if (0 == VG_(strlen)( VG_(indexXA)( ai->Addr.Variable.descr2, 0 ))) {
11407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      VG_(deleteXA)( ai->Addr.Variable.descr2 );
11507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      ai->Addr.Variable.descr2 = NULL;
11607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
11707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* Assume (assert) that VG_(get_data_description) fills in descr1
11807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      before it fills in descr2 */
11907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   if (ai->Addr.Variable.descr1 == NULL)
12007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      vg_assert(ai->Addr.Variable.descr2 == NULL);
12107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* So did we get lucky? */
12207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   if (ai->Addr.Variable.descr1 != NULL) {
12307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      ai->tag = Addr_Variable;
12407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      return;
12507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
12607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* -- Have a look at the low level data symbols - perhaps it's in
12707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      there. -- */
12846cc04521acf2827eb33310fadc119bf2dc039e4florian   const HChar *name;
12907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   if (VG_(get_datasym_and_offset)(
13046cc04521acf2827eb33310fadc119bf2dc039e4florian             a, &name,
13107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe             &ai->Addr.DataSym.offset )) {
13246cc04521acf2827eb33310fadc119bf2dc039e4florian      ai->Addr.DataSym.name = VG_(strdup)("mc.da.dsname", name);
13307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      ai->tag = Addr_DataSym;
13407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      return;
13507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
13607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* -- Perhaps it's on a thread's stack? -- */
13718d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe   {
1387e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      ThreadId   tid;
13918d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe      Addr       stack_min, stack_max;
14018d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe      VG_(thread_stack_reset_iter)(&tid);
14118d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe      while ( VG_(thread_stack_next)(&tid, &stack_min, &stack_max) ) {
14218d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe         if (stack_min - VG_STACK_REDZONE_SZB <= a && a <= stack_max) {
14318d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            Addr ips[VG_(clo_backtrace_size)],
14418d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                 sps[VG_(clo_backtrace_size)];
14518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            UInt n_frames;
14618d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            UInt f;
14718d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe
14818d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            ai->tag            = Addr_Stack;
1490c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe            VG_(initThreadInfo)(&ai->Addr.Stack.tinfo);
1500c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe            ai->Addr.Stack.tinfo.tid = tid;
15118d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            ai->Addr.Stack.IP = 0;
15218d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            ai->Addr.Stack.frameNo = -1;
1537e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            ai->Addr.Stack.stackPos = StackPos_stacked;
1547e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            ai->Addr.Stack.spoffset = 0; // Unused.
15518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            /* It is on thread tid stack. Build a stacktrace, and
15618d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               find the frame sp[f] .. sp[f+1] where the address is.
15718d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               Store the found frameNo and the corresponding IP in
15818d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               the description.
15918d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               When description is printed, IP will be translated to
16018d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               the function name containing IP.
16118d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               Before accepting to describe addr with sp[f] .. sp[f+1],
16218d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               we verify the sp looks sane: reasonably sized frame,
16318d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               inside the stack.
16418d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               We could check the ABI required alignment for sp (what is it?)
16518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               is respected, except for the innermost stack pointer ? */
16618d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            n_frames = VG_(get_StackTrace)( tid, ips, VG_(clo_backtrace_size),
16718d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                                            sps, NULL, 0/*first_ip_delta*/ );
16818d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            for (f = 0; f < n_frames-1; f++) {
16918d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               if (sps[f] <= a && a < sps[f+1]
17018d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                   && sps[f+1] - sps[f] <= 0x4000000 // 64 MB, arbitrary
17118d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                   && sps[f+1] <= stack_max
17218d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                   && sps[f]   >= stack_min - VG_STACK_REDZONE_SZB) {
17318d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                  ai->Addr.Stack.frameNo = f;
17418d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                  ai->Addr.Stack.IP = ips[f];
17518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                  break;
17618d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               }
17718d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            }
17818d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            return;
17918d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe         }
18007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      }
18107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
18207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
18307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* -- Maybe it is in one of the m_mallocfree.c arenas. --  */
18407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   {
18507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      AddrArenaInfo aai;
18607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      VG_(describe_arena_addr) ( a, &aai );
18707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      if (aai.name != NULL) {
18807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         ai->tag = Addr_Block;
18907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (aai.aid == VG_AR_CLIENT)
19007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            ai->Addr.Block.block_kind
19107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               = aai.free ? Block_ClientArenaFree : Block_ClientArenaMallocd;
19207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         else
19307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            ai->Addr.Block.block_kind
19407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               = aai.free
19507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                  ? Block_ValgrindArenaFree :  Block_ValgrindArenaMallocd;
19607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         ai->Addr.Block.block_desc = aai.name;
19707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         ai->Addr.Block.block_szB = aai.block_szB;
19807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         ai->Addr.Block.rwoffset = aai.rwoffset;
19907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         ai->Addr.Block.allocated_at = VG_(null_ExeContext)();
2000c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe         VG_(initThreadInfo) (&ai->Addr.Block.alloc_tinfo);
20107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         ai->Addr.Block.freed_at = VG_(null_ExeContext)();
20207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         return;
20307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      }
20407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
20507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
20607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* -- last ditch attempt at classification -- */
207e08950b4ce5a3f5d75a7279548f975cd6207dc74florian   sect = VG_(DebugInfo_sect_kind)( &name, a);
20807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   if (sect != Vg_SectUnknown) {
20907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      ai->tag = Addr_SectKind;
210dd2382088a3a598420286caa68e98f168a88bee3philippe      ai->Addr.SectKind.objname = VG_(strdup)("mc.da.dsname", name);
21107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      ai->Addr.SectKind.kind = sect;
21207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      return;
21307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
2147e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
2157e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   /* -- and yet another last ditch attempt at classification -- */
2167e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   /* If the address is in a stack between the stack bottom (highest byte)
2177e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      and the current stack ptr, it will have been already described above.
2187e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      But maybe it is in a stack, but below the stack ptr (typical
2197e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      for a 'use after return' or in the stack guard page (thread stack
2207e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      too small). */
2217e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   {
2227e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      ThreadId   tid;
223d099e51e1159ef5c27e066ddacc26b1866ec8e83philippe      StackPos stackPos = StackPos_stacked;
224d099e51e1159ef5c27e066ddacc26b1866ec8e83philippe      // Default init to StackPos_stacked, to silence gcc warning.
225ed39800a83baf5bffbe391f3974eb2af0f415f80Elliott Hughes      // We assert this value is overridden if a stack descr is produced.
2267e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
2277e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      // First try to find a tid with stack containing a
2287e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      tid = find_tid_with_stack_containing (a);
2297e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      if (tid != VG_INVALID_THREADID) {
2307e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         /* Should be below stack pointer, as if it is >= SP, it
2317e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            will have been described as StackPos_stacked above. */
2327e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         stackPos = StackPos_below_stack_ptr;
2337e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      } else {
2347e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         /* Try to find a stack with guard page containing a.
2357e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            For this, check if a is in a page mapped without r, w and x. */
2367e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         const NSegment *seg = VG_(am_find_nsegment) (a);
2377e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         if (seg != NULL && seg->kind == SkAnonC
2387e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe             && !seg->hasR && !seg->hasW && !seg->hasX) {
2397e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            /* This looks a plausible guard page. Check if a is close to
2407e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe               the start of stack (lowest byte). */
2417e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            tid = find_tid_with_stack_containing (VG_PGROUNDUP(a+1));
2427e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            if (tid != VG_INVALID_THREADID)
2437e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe               stackPos = StackPos_guard_page;
2447e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         }
2457e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      }
2467e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
2477e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      if (tid != VG_INVALID_THREADID) {
2487e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         ai->tag  = Addr_Stack;
2497e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         VG_(initThreadInfo)(&ai->Addr.Stack.tinfo);
2507e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         ai->Addr.Stack.tinfo.tid = tid;
2517e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         ai->Addr.Stack.IP = 0;
2527e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         ai->Addr.Stack.frameNo = -1;
253d099e51e1159ef5c27e066ddacc26b1866ec8e83philippe         vg_assert (stackPos != StackPos_stacked);
2547e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         ai->Addr.Stack.stackPos = stackPos;
2557e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         vg_assert (a < VG_(get_SP)(tid));
2567e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         ai->Addr.Stack.spoffset = a - VG_(get_SP)(tid);
2577e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         return;
2587e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe      }
2597e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe   }
2607e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
261f7ec77f53fd09a5682dbe6db049efe0746df7948philippe   /* -- and yet another last ditch attempt at classification -- */
262f7ec77f53fd09a5682dbe6db049efe0746df7948philippe   /* Try to find a segment belonging to the client. */
263f7ec77f53fd09a5682dbe6db049efe0746df7948philippe   {
264f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      const NSegment *seg = VG_(am_find_nsegment) (a);
265d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe
266d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe      /* Special case to detect the brk data segment. */
267d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe      if (seg != NULL
2688eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#if defined(VGO_solaris)
2698eb8bab992e3998c33770b0cdb16059a8b918a06sewardj          && (seg->kind == SkAnonC || seg->kind == SkFileC)
2708eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#else
271d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe          && seg->kind == SkAnonC
2728eb8bab992e3998c33770b0cdb16059a8b918a06sewardj#endif /* VGO_solaris */
273d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe          && VG_(brk_limit) >= seg->start
274d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe          && VG_(brk_limit) <= seg->end+1) {
275d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         /* Address a is in a Anon Client segment which contains
276d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            VG_(brk_limit). So, this segment is the brk data segment
277d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            as initimg-linux.c:setup_client_dataseg maps an anonymous
278d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            segment followed by a reservation, with one reservation
279d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            page that will never be used by syswrap-generic.c:do_brk,
280d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            when increasing VG_(brk_limit).
281d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            So, the brk data segment will never be merged with the
282d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            next segment, and so an address in that area will
283d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            either be in the brk data segment, or in the unmapped
284d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe            part of the brk data segment reservation. */
285d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         ai->tag = Addr_BrkSegment;
286d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         ai->Addr.BrkSegment.brk_limit = VG_(brk_limit);
287d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         return;
288d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe      }
289d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe
290f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      if (seg != NULL
291f7ec77f53fd09a5682dbe6db049efe0746df7948philippe          && (seg->kind == SkAnonC
292f7ec77f53fd09a5682dbe6db049efe0746df7948philippe              || seg->kind == SkFileC
293f7ec77f53fd09a5682dbe6db049efe0746df7948philippe              || seg->kind == SkShmC)) {
294f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         ai->tag = Addr_SegmentKind;
295f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         ai->Addr.SegmentKind.segkind = seg->kind;
296f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         ai->Addr.SegmentKind.filename = NULL;
297f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         if (seg->kind == SkFileC)
298d3166c4cf9d2545242da71d8baeaaf203b02a09dflorian            ai->Addr.SegmentKind.filename
299d3166c4cf9d2545242da71d8baeaaf203b02a09dflorian               = VG_(strdup)("mc.da.skfname", VG_(am_get_filename)(seg));
300f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         ai->Addr.SegmentKind.hasR = seg->hasR;
301f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         ai->Addr.SegmentKind.hasW = seg->hasW;
302f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         ai->Addr.SegmentKind.hasX = seg->hasX;
303f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         return;
304f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      }
305f7ec77f53fd09a5682dbe6db049efe0746df7948philippe   }
306f7ec77f53fd09a5682dbe6db049efe0746df7948philippe
30707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   /* -- Clueless ... -- */
30807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   ai->tag = Addr_Unknown;
30907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   return;
31007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe}
31107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
3120c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippevoid VG_(initThreadInfo) (ThreadInfo *tinfo)
3130c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe{
3140c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe   tinfo->tid = 0;
3150c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe   tinfo->tnr = 0;
3160c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe}
3170c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe
31807c08527f05caeb0062b42ca9a58ee774ec5fba1philippevoid VG_(clear_addrinfo) ( AddrInfo* ai)
31907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe{
32007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   switch (ai->tag) {
3210af05d465f338f7009ccb1172c61f00e06ddb58aphilippe      case Addr_Undescribed:
3220af05d465f338f7009ccb1172c61f00e06ddb58aphilippe         break;
3230af05d465f338f7009ccb1172c61f00e06ddb58aphilippe
32407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Unknown:
3250af05d465f338f7009ccb1172c61f00e06ddb58aphilippe         break;
32607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
32707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Stack:
3280af05d465f338f7009ccb1172c61f00e06ddb58aphilippe         break;
32907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
33007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Block:
33107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
33207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
33307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_DataSym:
33446cc04521acf2827eb33310fadc119bf2dc039e4florian         VG_(free)(ai->Addr.DataSym.name);
33507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
33607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
33707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Variable:
33807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (ai->Addr.Variable.descr1 != NULL) {
33907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(deleteXA)( ai->Addr.Variable.descr1 );
34007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            ai->Addr.Variable.descr1 = NULL;
34107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         }
34207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (ai->Addr.Variable.descr2 != NULL) {
34307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(deleteXA)( ai->Addr.Variable.descr2 );
34407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            ai->Addr.Variable.descr2 = NULL;
34507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         }
34607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
34707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
34807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_SectKind:
349e08950b4ce5a3f5d75a7279548f975cd6207dc74florian         VG_(free)(ai->Addr.SectKind.objname);
35007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
35107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
352d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe      case Addr_BrkSegment:
353d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         break;
354d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe
355f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      case Addr_SegmentKind:
356f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         VG_(free)(ai->Addr.SegmentKind.filename);
357f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         break;
358f7ec77f53fd09a5682dbe6db049efe0746df7948philippe
35907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      default:
36007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         VG_(core_panic)("VG_(clear_addrinfo)");
36107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
36207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
36307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   ai->tag = Addr_Undescribed;
36407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe}
36507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
36607c08527f05caeb0062b42ca9a58ee774ec5fba1philippestatic Bool is_arena_BlockKind(BlockKind bk)
36707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe{
36807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   switch (bk) {
36907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_Mallocd:
37007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_Freed:
37107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_MempoolChunk:
37207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_UserG:                return False;
37307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
37407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_ClientArenaMallocd:
37507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_ClientArenaFree:
37607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_ValgrindArenaMallocd:
37707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Block_ValgrindArenaFree:    return True;
37807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
37907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      default:                         vg_assert (0);
38007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
38107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe}
38207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
3830c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippestatic const HChar* opt_tnr_prefix (ThreadInfo tinfo)
3840c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe{
3850c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe   if (tinfo.tnr != 0)
3860c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe      return "#";
3870c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe   else
3880c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe      return "";
3890c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe}
3900c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe
3910c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippestatic UInt tnr_else_tid (ThreadInfo tinfo)
3920c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe{
3930c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe   if (tinfo.tnr != 0)
3940c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe      return tinfo.tnr;
3950c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe   else
3960c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe      return tinfo.tid;
3970c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe}
3980c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe
399f7ec77f53fd09a5682dbe6db049efe0746df7948philippestatic const HChar* pp_SegKind ( SegKind sk )
400f7ec77f53fd09a5682dbe6db049efe0746df7948philippe{
401f7ec77f53fd09a5682dbe6db049efe0746df7948philippe   switch (sk) {
402f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      case SkAnonC: return "anonymous";
403f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      case SkFileC: return "mapped file";
404f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      case SkShmC:  return "shared memory";
405f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      default:      vg_assert(0);
406f7ec77f53fd09a5682dbe6db049efe0746df7948philippe   }
407f7ec77f53fd09a5682dbe6db049efe0746df7948philippe}
408f7ec77f53fd09a5682dbe6db049efe0746df7948philippe
409518850bf0da07ed3e2244e307268ae0fd80e93a8florianstatic void pp_addrinfo_WRK ( Addr a, const AddrInfo* ai, Bool mc,
410518850bf0da07ed3e2244e307268ae0fd80e93a8florian                              Bool maybe_gcc )
41107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe{
41207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   const HChar* xpre  = VG_(clo_xml) ? "  <auxwhat>" : " ";
41307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   const HChar* xpost = VG_(clo_xml) ? "</auxwhat>"  : "";
41407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
41507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   vg_assert (!maybe_gcc || mc); // maybe_gcc can only be given in mc mode.
41607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
41707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   switch (ai->tag) {
4180af05d465f338f7009ccb1172c61f00e06ddb58aphilippe      case Addr_Undescribed:
4190af05d465f338f7009ccb1172c61f00e06ddb58aphilippe         VG_(core_panic)("mc_pp_AddrInfo Addr_Undescribed");
4200af05d465f338f7009ccb1172c61f00e06ddb58aphilippe
42107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Unknown:
42207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (maybe_gcc) {
423a5e06c36bf9d93461bc8c4351e960888020ea1c4florian            VG_(emit)( "%sAddress 0x%lx is just below the stack ptr.  "
42407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       "To suppress, use: --workaround-gcc296-bugs=yes%s\n",
425a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       xpre, a, xpost );
42607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe	 } else {
427a5e06c36bf9d93461bc8c4351e960888020ea1c4florian            VG_(emit)( "%sAddress 0x%lx "
42807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       "is not stack'd, malloc'd or %s%s\n",
429a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       xpre, a,
43007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       mc ? "(recently) free'd" : "on a free list",
43107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       xpost );
43207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         }
43307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
43407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
43507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Stack:
436a5e06c36bf9d93461bc8c4351e960888020ea1c4florian         VG_(emit)( "%sAddress 0x%lx is on thread %s%u's stack%s\n",
437a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                    xpre, a,
4380c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe                    opt_tnr_prefix (ai->Addr.Stack.tinfo),
4390c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe                    tnr_else_tid (ai->Addr.Stack.tinfo),
4400c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe                    xpost );
44118d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe         if (ai->Addr.Stack.frameNo != -1 && ai->Addr.Stack.IP != 0) {
44246cc04521acf2827eb33310fadc119bf2dc039e4florian            const HChar *fn;
44318d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            Bool  hasfn;
44410ef725f1e8e9f1615c483555348eb75b69c4713florian            const HChar *file;
44518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            Bool  hasfile;
44618d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            UInt linenum;
44718d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            Bool haslinenum;
44818d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            PtrdiffT offset;
44918d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe
45018d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            if (VG_(get_inst_offset_in_function)( ai->Addr.Stack.IP,
45118d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                                                  &offset))
45218d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               haslinenum = VG_(get_linenum) (ai->Addr.Stack.IP - offset,
45318d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                                              &linenum);
45418d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            else
45518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe               haslinenum = False;
45618d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe
45710ef725f1e8e9f1615c483555348eb75b69c4713florian            hasfile = VG_(get_filename)(ai->Addr.Stack.IP, &file);
45810ef725f1e8e9f1615c483555348eb75b69c4713florian
45910ef725f1e8e9f1615c483555348eb75b69c4713florian            HChar strlinenum[16] = "";   // large enough
46010ef725f1e8e9f1615c483555348eb75b69c4713florian            if (hasfile && haslinenum)
461a5e06c36bf9d93461bc8c4351e960888020ea1c4florian               VG_(sprintf)(strlinenum, "%u", linenum);
46218d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe
46346cc04521acf2827eb33310fadc119bf2dc039e4florian            hasfn = VG_(get_fnname)(ai->Addr.Stack.IP, &fn);
46446cc04521acf2827eb33310fadc119bf2dc039e4florian
46518d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe            if (hasfn || hasfile)
466a0664b9ca67b594bd6f570a61d3301167a24750cElliott Hughes               VG_(emit)( "%sin frame #%d, created by %ps (%ps:%s)%s\n",
46718d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                          xpre,
46818d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                          ai->Addr.Stack.frameNo,
46918d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                          hasfn ? fn : "???",
47010ef725f1e8e9f1615c483555348eb75b69c4713florian                          hasfile ? file : "???", strlinenum,
47118d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe                          xpost );
47218d6f4ec1b86057e1a906db1a1d31c89472fb1adphilippe         }
4737e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         switch (ai->Addr.Stack.stackPos) {
4747e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            case StackPos_stacked: break; // nothing more to say
4757e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
4767e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            case StackPos_below_stack_ptr:
4777e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            case StackPos_guard_page:
4787e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                VG_(emit)("%s%s%ld bytes below stack pointer%s\n",
4797e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                          xpre,
4807e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                          ai->Addr.Stack.stackPos == StackPos_guard_page ?
4817e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                          "In stack guard protected page, " : "",
4827e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                          - ai->Addr.Stack.spoffset,
4837e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                          xpost);
4847e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                // Note: we change the sign of spoffset as the message speaks
4857e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                // about the nr of bytes below stack pointer.
4867e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe                break;
4877e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe
4887e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe            default: vg_assert(0);
4897e3b3f23b41ae75ceb6306ea3e15f110bbbf3dd6philippe         }
49007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
49107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
49207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Block: {
49307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         SizeT    block_szB = ai->Addr.Block.block_szB;
49407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         PtrdiffT rwoffset  = ai->Addr.Block.rwoffset;
49507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         SizeT    delta;
49607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         const    HChar* relative;
49707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
49807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (rwoffset < 0) {
49907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            delta    = (SizeT)(-rwoffset);
50007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            relative = "before";
50107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         } else if (rwoffset >= block_szB) {
50207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            delta    = rwoffset - block_szB;
50307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            relative = "after";
50407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         } else {
50507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            delta    = rwoffset;
50607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            relative = "inside";
50707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         }
50807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (is_arena_BlockKind (ai->Addr.Block.block_kind))
50907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(emit)(
51007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               "%sAddress 0x%lx is %'lu bytes %s a%s block of size %'lu"
51107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               " in arena \"%s\"%s\n",
51207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               xpre,
51307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               a, delta,
51407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               relative,
51507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               ai->Addr.Block.block_kind==Block_ClientArenaMallocd
51607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                 || ai->Addr.Block.block_kind==Block_ValgrindArenaMallocd
51707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                 ? "" : "n unallocated",
51807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               block_szB,
51907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               ai->Addr.Block.block_desc,  // arena name
52007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               xpost
52107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            );
52207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         else
52307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(emit)(
52407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               "%sAddress 0x%lx is %'lu bytes %s a %s of size %'lu %s%s\n",
52507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               xpre,
52607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               a, delta,
52707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               relative,
52807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               ai->Addr.Block.block_desc,
52907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               block_szB,
53007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               ai->Addr.Block.block_kind==Block_Mallocd ? "alloc'd"
53107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               : ai->Addr.Block.block_kind==Block_Freed ? "free'd"
53207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                                                        : "client-defined",
53307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               xpost
53407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            );
53507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (ai->Addr.Block.block_kind==Block_Mallocd) {
53607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(pp_ExeContext)(ai->Addr.Block.allocated_at);
537e2800c958044937e72eefa371c10ae47ac40e089florian            vg_assert (ai->Addr.Block.freed_at == VG_(null_ExeContext)());
53807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         }
53907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         else if (ai->Addr.Block.block_kind==Block_Freed) {
54007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(pp_ExeContext)(ai->Addr.Block.freed_at);
54107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            if (ai->Addr.Block.allocated_at != VG_(null_ExeContext)()) {
54207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               VG_(emit)(
5430c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe                  "%sBlock was alloc'd at%s\n",
54407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                  xpre,
54507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                  xpost
54607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               );
54707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               VG_(pp_ExeContext)(ai->Addr.Block.allocated_at);
54807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            }
54907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         }
55007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         else if (ai->Addr.Block.block_kind==Block_MempoolChunk
55107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                  || ai->Addr.Block.block_kind==Block_UserG) {
55207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            // client-defined
55307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(pp_ExeContext)(ai->Addr.Block.allocated_at);
554e2800c958044937e72eefa371c10ae47ac40e089florian            vg_assert (ai->Addr.Block.freed_at == VG_(null_ExeContext)());
55507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            /* Nb: cannot have a freed_at, as a freed client-defined block
55607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe               has a Block_Freed block_kind. */
55707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         } else {
55807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            // Client or Valgrind arena. At least currently, we never
55907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            // have stacktraces for these.
560e2800c958044937e72eefa371c10ae47ac40e089florian            vg_assert (ai->Addr.Block.allocated_at == VG_(null_ExeContext)());
561e2800c958044937e72eefa371c10ae47ac40e089florian            vg_assert (ai->Addr.Block.freed_at == VG_(null_ExeContext)());
56207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         }
5630c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe         if (ai->Addr.Block.alloc_tinfo.tnr || ai->Addr.Block.alloc_tinfo.tid)
5640c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe            VG_(emit)(
565a5e06c36bf9d93461bc8c4351e960888020ea1c4florian               "%sBlock was alloc'd by thread %s%u%s\n",
5660c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe               xpre,
5670c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe               opt_tnr_prefix (ai->Addr.Block.alloc_tinfo),
5680c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe               tnr_else_tid (ai->Addr.Block.alloc_tinfo),
5690c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe               xpost
5700c9ac8d0deca2f2a552fb2b0cab24efe6191bac7philippe            );
57107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
57207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      }
57307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
57407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_DataSym:
575a5e06c36bf9d93461bc8c4351e960888020ea1c4florian         VG_(emit)( "%sAddress 0x%lx is %llu bytes "
576a0664b9ca67b594bd6f570a61d3301167a24750cElliott Hughes                    "inside data symbol \"%ps\"%s\n",
577a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                    xpre, a,
57807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    (ULong)ai->Addr.DataSym.offset,
57907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    ai->Addr.DataSym.name,
58007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    xpost );
58107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
58207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
58307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_Variable:
58407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         /* Note, no need for XML tags here, because descr1/2 will
58507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            already have <auxwhat> or <xauxwhat>s on them, in XML
58607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            mode. */
58707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (ai->Addr.Variable.descr1)
58807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(emit)( "%s%s\n",
58907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       VG_(clo_xml) ? "  " : " ",
59007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       (HChar*)VG_(indexXA)(ai->Addr.Variable.descr1, 0) );
59107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         if (ai->Addr.Variable.descr2)
59207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe            VG_(emit)( "%s%s\n",
59307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       VG_(clo_xml) ? "  " : " ",
59407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                       (HChar*)VG_(indexXA)(ai->Addr.Variable.descr2, 0) );
59507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
59607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
59707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      case Addr_SectKind:
598a0664b9ca67b594bd6f570a61d3301167a24750cElliott Hughes         VG_(emit)( "%sAddress 0x%lx is in the %ps segment of %ps%s\n",
599a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                    xpre, a,
60007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    VG_(pp_SectKind)(ai->Addr.SectKind.kind),
60107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    ai->Addr.SectKind.objname,
60207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe                    xpost );
603a7cea052061af7ffa79d06feb69d7d129c5bf0efphilippe         if (ai->Addr.SectKind.kind == Vg_SectText) {
604a7cea052061af7ffa79d06feb69d7d129c5bf0efphilippe            /* To better describe the address in a text segment,
605a7cea052061af7ffa79d06feb69d7d129c5bf0efphilippe               pp a dummy stacktrace made of this single address. */
606a7cea052061af7ffa79d06feb69d7d129c5bf0efphilippe            VG_(pp_StackTrace)( &a, 1 );
607a7cea052061af7ffa79d06feb69d7d129c5bf0efphilippe         }
60807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe         break;
60907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
610d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe      case Addr_BrkSegment:
611d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         if (a < ai->Addr.BrkSegment.brk_limit)
612a5e06c36bf9d93461bc8c4351e960888020ea1c4florian            VG_(emit)( "%sAddress 0x%lx is in the brk data segment"
613a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       " 0x%lx-0x%lx%s\n",
614a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       xpre, a,
615a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       VG_(brk_base),
616a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       ai->Addr.BrkSegment.brk_limit - 1,
617d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe                       xpost );
618d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         else
619a5e06c36bf9d93461bc8c4351e960888020ea1c4florian            VG_(emit)( "%sAddress 0x%lx is %lu bytes after "
620d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe                       "the brk data segment limit"
621a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       " 0x%lx%s\n",
622a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       xpre, a,
623d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe                       a - ai->Addr.BrkSegment.brk_limit,
624a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                       ai->Addr.BrkSegment.brk_limit,
625d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe                       xpost );
626d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe         break;
627d0da968735a4986e3a23f0832e9173fa9d58a1a3philippe
628f7ec77f53fd09a5682dbe6db049efe0746df7948philippe      case Addr_SegmentKind:
629a5e06c36bf9d93461bc8c4351e960888020ea1c4florian         VG_(emit)( "%sAddress 0x%lx is in "
630a0664b9ca67b594bd6f570a61d3301167a24750cElliott Hughes                    "a %s%s%s %s%s%ps segment%s\n",
631f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    xpre,
632a5e06c36bf9d93461bc8c4351e960888020ea1c4florian                    a,
633f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    ai->Addr.SegmentKind.hasR ? "r" : "-",
634f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    ai->Addr.SegmentKind.hasW ? "w" : "-",
635f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    ai->Addr.SegmentKind.hasX ? "x" : "-",
636f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    pp_SegKind(ai->Addr.SegmentKind.segkind),
637f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    ai->Addr.SegmentKind.filename ?
638f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    " " : "",
639f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    ai->Addr.SegmentKind.filename ?
640f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    ai->Addr.SegmentKind.filename : "",
641f7ec77f53fd09a5682dbe6db049efe0746df7948philippe                    xpost );
642f7ec77f53fd09a5682dbe6db049efe0746df7948philippe         break;
643f7ec77f53fd09a5682dbe6db049efe0746df7948philippe
64407c08527f05caeb0062b42ca9a58ee774ec5fba1philippe      default:
645a4ca4fef8c189e861492e1e2b36b52ba3fca1725florian         VG_(core_panic)("mc_pp_AddrInfo");
64607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   }
64707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe}
64807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
649518850bf0da07ed3e2244e307268ae0fd80e93a8florianvoid VG_(pp_addrinfo) ( Addr a, const AddrInfo* ai )
65007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe{
65107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   pp_addrinfo_WRK (a, ai, False /*mc*/, False /*maybe_gcc*/);
65207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe}
65307c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
654518850bf0da07ed3e2244e307268ae0fd80e93a8florianvoid VG_(pp_addrinfo_mc) ( Addr a, const AddrInfo* ai, Bool maybe_gcc )
65507c08527f05caeb0062b42ca9a58ee774ec5fba1philippe{
65607c08527f05caeb0062b42ca9a58ee774ec5fba1philippe   pp_addrinfo_WRK (a, ai, True /*mc*/, maybe_gcc);
65707c08527f05caeb0062b42ca9a58ee774ec5fba1philippe}
65807c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
65907c08527f05caeb0062b42ca9a58ee774ec5fba1philippe
66007c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*--------------------------------------------------------------------*/
66107c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*--- end                                             m_addrinfo.c ---*/
66207c08527f05caeb0062b42ca9a58ee774ec5fba1philippe/*--------------------------------------------------------------------*/
663