I am seeing different ways of starting threads in ubuntu and in other linux platform.
pthread_create ( &thread1, NULL, (void *) &myfun1, (void *) msg1);
pthread_create ( &thread2, NULL, (void *) &myfun2, (void *) msg2);
pthread_create ( &thread3, NULL, (void *) &myfun3, (void *) msg3);
pthread_create ( &thread4, NULL, (void *) &myfun4, (void *) msg4);
In the above case of ubuntu , first the thread4 is starting while in case of other linux os it's the thread1. When I checked reason, seems to be because of scheduling policies(correct me if i am wrong).
In these cases how to ensure that the always the first thread (thread1) executes first despite of different linux flavours.
/Generic query/, does the scheduling policy does not depend upon kernel ? Because two different types of thread execution is seen in the different linux flavours.
Pseudo code that makes thread 1 start before the other thread execute the tasks:
Mutex mutex = ... /* static init here */
Condition cond = ... /* static init here */
boolean first_thread_running = false;
thread1
{
mutex_lock
first_thread_running = true;
cond_signal
mutex_unlock
/* do things */
}
thread<N> /* with <N> = {2, 3, 4} */
{
mutex_lock
while (not first_thread_running)
cond_wait
mutex_unlock
/* thread1 definitly runs now */
/* do things */
}
main
{
/* The order of the following statements does not matter, thread 1
will always be started before the other threads "do their things". */
thread4_create
thread2_create
thread1_create
thread3_create
...
Related
While implementing a stack walker for a debugger I am working on I reached the point to extract the arguments to a function call and display them. To make it simple I started with the cdecl convention in pure 32-bit (both debugger and debuggee), and a function that takes 3 parameters. However, I cannot understand why the arguments in the stack trace are out of order compared to what cdecl defines (right-to-left, nothing in registers), despite trying to figure it out for a few days now.
Here is a representation of the function call I am trying to stack trace:
void Function(unsigned long long a, const void * b, unsigned int c) {
printf("a=0x%llX, b=%p, c=0x%X\n", a, b, c);
_asm { int 3 }; /* Because I don't have stepping or dynamic breakpoints implemented yet */
}
int main(int argc, char* argv[]) {
Function(2, (void*)0x7A3FE8, 0x2004);
return 0;
}
This is what the function (unsurprisingly) printed to the console:
a=0x2, c=0x7a3fe8, c=0x2004
This is the stack trace generated at the breakpoint (the debugger catches the breakpoint and there I try to walk the stack):
0x3EF5E0: 0x10004286 /* previous pc */
0x3EF5DC: 0x3EF60C /* previous fp */
0x3EF5D8: 0x7A3FE8 /* arg b --> Wait... why is b _above_ c here? */
0x3EF5D4: 0x2004 /* arg c */
0x3EF5D0: 0x0 /* arg a, upper 32 bit */
0x3EF5CC: 0x2 /* arg a, lower 32 bit */
The code that's responsible for dumping the stack frames (implemented using the DIA SDK, though, I don't think that is relevant to my problem) looks like this:
ULONGLONG stackframe_top = 0;
m_frame->get_base(&stackframe_top); /* IDiaStackFrame */
/* dump 30 * 4 bytes */
for (DWORD i = 0; i < 30; i++)
{
ULONGLONG address = stackframe_top - (i * 4);
DWORD value;
SIZE_T read_bytes;
if (ReadProcessMemory(m_process, reinterpret_cast<LPVOID>(address), &value, sizeof(value), &read_bytes) == TRUE)
{
debugprintf(L"0x%llX: 0x%X\n", address, value); /* wrapper around OutputDebugString */
}
}
I am compiling the test program without any optimization in vs2015 update 3.
I have validated that I am indeed compiling it as cdecl by looking in the pdb with the dia2dump sample application.
I do not understand what is causing the stack to look like this, it doesn't match anything I learned, nor does it match the documentation provided by Microsoft.
I also checked google a whole lot (including osdev wiki pages, msdn blog posts, and so on), and checked my (by now probably outdated) books on 32-bit x86 assembly programming (that were released before 64-bit CPUs existed).
Thank you very much in advance for any explanations or links!
I had somehow misunderstood where the arguments to a function call end up in memory compared to the base of the stack frame, as pointed out by Raymond. This is the fixed code snippet:
ULONGLONG stackframe_top = 0;
m_frame->get_base(&stackframe_top); /* IDiaStackFrame */
/* dump 30 * 4 bytes */
for (DWORD i = 0; i < 30; i++)
{
ULONGLONG address = stackframe_top + (i * 4); /* <-- Read before the stack frame */
DWORD value;
SIZE_T read_bytes;
if (ReadProcessMemory(m_process, reinterpret_cast<LPVOID>(address), &value, sizeof(value), &read_bytes) == TRUE)
{
debugprintf(L"0x%llX: 0x%X\n", address, value); /* wrapper around OutputDebugString */
}
}
Is it possible to set a watchpoint on pthread's thread-local storage using GDB? I have a program that runs:
struct stored_type *res = pthread_getspecific(tls_key);
...and after a few thousand calls it returns 0 instead of a valid pointer. I'd really love to figure out what's setting that value to 0. I've tried setting breakpoints on pthread_setspecific and pthread_delete_key (the only things I could think of that would reasonably cause the key to change value) and those breakpoints aren't getting hit, so I'm thinking there's some kind of overrun happening.
I'm using Linux x86_64 with glibc 2.23.
... the only things I could think of that would reasonably cause the key to change value
The most likely reasons for pthread_getspecific to return NULL:
you are in fact executing in a new thread, one in which pthread_setspecific hasn't been called,
you are calling pthread_getspecific while current thread is in the process of being destroyed (i.e. pthread_exit is somewhere on the stack),
you are calling pthread_getspecific in a signal handler (none of pthread_* functions are async-signal safe).
Assuming none of the above reasons are true in your case, on with the show.
First we need a test case to demonstrate on.
#include <assert.h>
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
pthread_key_t key;
void *thrfn(void *p) {
int rc = pthread_setspecific(key, &p);
assert(rc == 0);
sleep(60);
rc = pthread_setspecific(key, (void*)0x112233);
assert(rc == 0);
return p;
}
int main()
{
pthread_t thr;
int rc = pthread_key_create(&key, NULL);
assert(rc == 0);
rc = pthread_create(&thr, NULL, thrfn, NULL);
assert(rc == 0);
sleep(90);
return 0;
}
gcc -g -pthread t.c
gdb -q ./a.out
(gdb) start
Now, it helps very much to have GLIBC that is compiled with debug info. Most distributions provide a libc-dbg or similar package, which supplies that. Looking at pthread_setspecific source, you can see that inside the thread descriptor (self) there is a specific_1stblock array, where the space for first PTHREAD_KEY_2NDLEVEL_SIZE == 32 key slots is pre-allocated (32 distinct keys is usually more than enough).
The value that we pass will be stored in self->specific_1stblock[key].data, and that's exactly the location you'll want to set the watchpoint on.
In our sample program, key == 0 (as this is the very first key). Putting it all together:
Starting program: /tmp/a.out
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib64/libthread_db.so.1".
Temporary breakpoint 1, main () at t.c:21
21 int rc = pthread_key_create(&key, NULL);
(gdb) b pthread_setspecific
Breakpoint 2 at 0x7ffff7bc9460: file pthread_setspecific.c, line 28.
(gdb) c
Continuing.
[New Thread 0x7ffff77f6700 (LWP 58683)]
[Switching to Thread 0x7ffff77f6700 (LWP 58683)]
Breakpoint 2, __GI___pthread_setspecific (key=0, value=0x7ffff77f5ef8) at pthread_setspecific.c:28
28 pthread_setspecific.c: No such file or directory.
(gdb) n
35 in pthread_setspecific.c
(gdb) n
28 in pthread_setspecific.c
(gdb) p self
$1 = (struct pthread *) 0x7ffff77f6700
(gdb) watch -l self.specific_1stblock[key].data
Hardware watchpoint 3: -location self.specific_1stblock[key].data
(gdb) c
Continuing.
Hardware watchpoint 3: -location self.specific_1stblock[key].data
Old value = (void *) 0x0
New value = (void *) 0x7ffff77f5ef8
__GI___pthread_setspecific (key=<optimized out>, value=0x7ffff77f5ef8) at pthread_setspecific.c:89
89 in pthread_setspecific.c
Note that the new value is exactly the value that we passed to pthread_setspecific.
(gdb) c
Continuing.
Breakpoint 2, __GI___pthread_setspecific (key=0, value=0x112233) at pthread_setspecific.c:28
28 in pthread_setspecific.c
(gdb) c
Continuing.
Hardware watchpoint 3: -location self.specific_1stblock[key].data
Old value = (void *) 0x7ffff77f5ef8
New value = (void *) 0x112233
__GI___pthread_setspecific (key=<optimized out>, value=0x112233) at pthread_setspecific.c:89
89 in pthread_setspecific.c
This is our second pthread_setspecific call
(gdb) c
Continuing.
Hardware watchpoint 3: -location self.specific_1stblock[key].data
Old value = (void *) 0x112233
New value = (void *) 0x0
__nptl_deallocate_tsd () at pthread_create.c:152
152 pthread_create.c: No such file or directory.
And this is thread destruction, which deallocates the thread descriptor itself.
(gdb) c
Continuing.
[Thread 0x7ffff77f6700 (LWP 58683) exited]
[Inferior 1 (process 58677) exited normally]
I've been trying to setup SEH on x64 windows using gcc by calling the RtlAddFunctionTable. Unfortunately, the API call returns success but my handler doesn't seem to ever be called. And I can't find out what's wrong. My small example is:
EXCEPTION_DISPOSITION catchDivZero( struct _EXCEPTION_RECORD* rec
, void* arg1 __attribute__((unused))
, struct _CONTEXT* ctxt __attribute__((unused))
, void* arg2 __attribute__((unused))
)
{
printf("Exception will be handled!\n");
return ExceptionContinueSearch;
}
HMODULE GetCurrentModule()
{ // NB: XP+ solution!
HMODULE hModule = NULL;
GetModuleHandleEx(
GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS,
(LPCTSTR)GetCurrentModule,
&hModule);
return hModule;
}
typedef struct {
UINT8 Version : 3;
UINT8 Flags : 5;
UINT8 SizeOfProlog;
UINT8 CountOfUnwindCodes;
UINT8 FrameRegister : 4;
UINT8 FrameRegisterOffset : 4;
ULONG ExceptionHandler;
} UNWIND_INFO;
/* Hack, for bug in ld. Will be removed soon. */
#if defined(__GNUC__)
#define __ImageBase __MINGW_LSYMBOL(_image_base__)
#endif
/* Get the end of the text section. */
extern char etext[] asm("etext");
/* Get the base of the module. */
/* This symbol is defined by ld. */
extern IMAGE_DOS_HEADER __ImageBase;
static UNWIND_INFO info[1];
static RUNTIME_FUNCTION handlers[1];
#define base (ULONG)((HINSTANCE)&__ImageBase)
int main()
{
HANDLE hProcess = GetCurrentProcess();
HMODULE hModule = GetCurrentModule();
MODULEINFO mi;
GetModuleInformation(hProcess, hModule, &mi, sizeof(mi));
printf( "Module: 0x%.8X (0x%.8X) 0x%.8X |0x%.8X| [0x%.8X] {0x%.8X}\n\n"
, mi.lpBaseOfDll
, base
, (char*)etext
, mi.SizeOfImage
, &catchDivZero
, (ULONG)(&catchDivZero - base)
);
printf("Building UNWIND_INFO..\n");
info[0].Version = 1;
info[0].Flags = UNW_FLAG_EHANDLER;
info[0].SizeOfProlog = 0;
info[0].CountOfUnwindCodes = 0;
info[0].FrameRegister = 0;
info[0].FrameRegisterOffset = 0;
info[0].ExceptionHandler = (ULONG)(&catchDivZero - base);
printf("Created UNWIND_INFO at {0x%.8X}\n", info[0].ExceptionHandler);
printf("Building SEH handlers...\n");
handlers[0].BeginAddress = 0;
handlers[0].EndAddress = (ULONG)(etext - base);
handlers[0].UnwindData = (ULONG)((char*)info - base);
printf("Adding SEH handlers to .pdata..\n");
printf("Handler Unwind: 0x%.8X\n", &info);
printf( "Handler Info:: s: 0x%.8X, e: 0x%.8X, u: 0x%.8X\n"
, handlers[0].BeginAddress
, handlers[0].EndAddress
, handlers[0].UnwindData
);
if (RtlAddFunctionTable(handlers, 1, (DWORD64)base))
{
printf("Hook succeeded.\nTesting..\n");
printf("Things to do: %i\n", 12 / 0);
}
else
{
printf("Hook failed\n");
DWORD result = GetLastError();
printf("Error code: 0x%.8X\n", result);
}
}
However when called the output I get is:
> .\a.exe
Module: 0x00400000 (0x00400000) 0x00402FF0 |0x00022000| [0x00401530] {0x00001530}
Building UNWIND_INFO..
Created UNWIND_INFO at {0x00001530}
Building SEH handlers...
Adding SEH handlers to .pdata..
Handler Unwind: 0x00407030
Handler Info:: s: 0x00000000, e: 0x00002FF0, u: 0x00007030
Hook succeeded.
Testing..
The message in my handler is never printed.
Any help/pointers would be greatly appreciated.
RtlAddFunctionTable() adds a dynamic function table; if there already is a static function table (.pdata section) for the base address, the RtlAddFunctionTable() calls succeeds, but the static function table still takes precedence.
You need to allocate memory outside the image range, e.g. using VirtualAlloc(), and have your code and runtime table and unwind info there. The address of allocated memory is the base address for all the RVAs in the tables, and needs to be passed to RtlAddFunctionTable().
You can experiment with RtlLookupFunctionEntry() to see if the function table entry is found for a given address.
Sample code showing RtlAddFunctionTable() in action is at https://pmeerw.net/blog/programming/RtlAddFunctionTable.html.
Didn't you forget to register your handler with call to SetUnhandledExceptionFilter (if you use SEH as stated in your post) or AddVectoredExceptionHandler (if you decide to switch to VEH)? In your code you add information about the handler but do not register it.
I have tested your sample with the change of the handler itself:
LONG WINAPI catchDivZero(EXCEPTION_POINTERS * ExceptionInfo)
{
printf("Exception will be handled!\n");
return ExceptionContinueSearch;
}
and adding the code:
if (::AddVectoredExceptionHandler(TRUE, catchDivZero))
{
printf("Set exception handler.\nContinuing..\n");
}
else
{
printf("Setting exception handler failed\n");
DWORD result = GetLastError();
printf("Error code: 0x%.8X\n", result);
return 1;
}
just before the call to RtlAddFunctionTable.
Now the message from the handler is printed.
To remove the handler use:
::RemoveVectoredExceptionHandler(catchDivZero);
Hope it helps.
Note: as an alternative you may use SetUnhandledExceptionFilter(catchDivZero)). Keep in mind that it's not that useful for debugging:
After calling this function, if an exception occurs in a process that
is not being debugged, and the exception makes it to the unhandled
exception filter, that filter will call the exception filter function
specified by the lpTopLevelExceptionFilter parameter.
With VEH way we can debug the handler function right in IDE, with SEH we can not (there is probably a solution to this but I do not know about it) so I've proposed VEH as the main solution.
I have an application that I need to run at a 10mSec rate (100hz) on a Windows 7/32 bit computer (that will also be running other applications at the same time). This interrupt can have some minimally late (100uSec) responses, but must not drift over a prolonged time. I have a program where I have loaded and used the NtSetTimerResolution to set the timers to 10msec resolution, and then created a timer using the CreateTimerQueue/CreateTimereQueueTimer functions with a callback routine that toggles a GPIO pin (for the time being) - this produces the expected square wave, so long as I am not doing anything else with the system. When I start a couple of other processes, the accuracy of my square wave goes out the window. Is there any way to get a higher priority level on the timer interrupt (or is there another timer that I can use) that will produce a more stable output (perhaps the SMI)? My code is below, and is built using the x86 checked build environment of the Windows DDK, and run from a command shell with administrator rights:
/*
Abstract:
Simple console test app for a 10mSec timer interrupt service
Enviroment:
Administrator Mode
*/
/* INCLUDES */
#include <windows.h>
#include <winioctl.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <conio.h>
#include <strsafe.h>
#include <stdlib.h>
#include <stdio.h>
#include <winsock2.h>
#include <mswsock.h>
#pragma warning(disable:4127) // condition expression is constant
FARPROC pNtQueryTimerResolution;
FARPROC pNtSetTimerResolution;
static HANDLE NTDLLModuleHandle;
static HINSTANCE hInpOutDll;
typedef void ( __stdcall *lpOut32 )( short , short );
typedef short ( __stdcall *lpInp32 )( short );
typedef BOOL ( __stdcall *lpIsInpOutDriverOpen )( void );
//Some global function pointers (messy but fine for an example)
lpOut32 gfpOut32;
lpInp32 gfpInp32;
lpIsInpOutDriverOpen gfpIsInpOutDriverOpen;
void CALLBACK TimerProc(void* lpParameter,
BOOLEAN TimerOrWaitFired);
// MAIN
VOID __cdecl main( void )
{
ULONG ulMinRes = 0;
ULONG ulMaxRes = 0;
ULONG ulCurRes = 0;
HANDLE phNewQueue;
HANDLE phNewTimer;
phNewQueue = CreateTimerQueue( );
NTDLLModuleHandle = LoadLibrary( "NTDLL.DLL" );
if( NULL == NTDLLModuleHandle )
{
return;
}
// Get the function pointers,
pNtQueryTimerResolution = GetProcAddress( NTDLLModuleHandle, "NtQueryTimerResolution" );
pNtSetTimerResolution = GetProcAddress( NTDLLModuleHandle, "NtSetTimerResolution" );
if( ( pNtQueryTimerResolution == NULL ) || ( pNtSetTimerResolution == NULL ) )
{
printf( "unable to link to ddl\n\n\n\n\n\n" );
return;
}
pNtQueryTimerResolution( &ulMinRes, &ulMaxRes, &ulCurRes );
printf( "MMR: %d %d %d\n", ulMinRes, ulMaxRes, ulCurRes );
ulMaxRes = 100000;
pNtSetTimerResolution( ulMaxRes, TRUE, &ulCurRes );
pNtQueryTimerResolution( &ulMinRes, &ulMaxRes, &ulCurRes );
printf( "MMR: %d %d %d\n", ulMinRes, ulMaxRes, ulCurRes );
//Dynamically load the DLL at runtime (not linked at compile time)
hInpOutDll = LoadLibrary( "InpOut32.DLL" );
if( hInpOutDll != NULL )
{
gfpOut32 = ( lpOut32 )GetProcAddress( hInpOutDll, "Out32" );
gfpInp32 = ( lpInp32 )GetProcAddress( hInpOutDll, "Inp32" );
gfpIsInpOutDriverOpen
= ( lpIsInpOutDriverOpen )GetProcAddress( hInpOutDll, "IsInpOutDriverOpen" );
if( gfpIsInpOutDriverOpen( ) )
{
gfpOut32( 0xA01, 0x00 );
}
else
{
printf( "unable to create timer system\n\n\n\n\n\n" );
return;
}
}
CreateTimerQueueTimer( &phNewTimer, phNewQueue, TimerProc, NULL, 0, 10,
WT_EXECUTEINTIMERTHREAD );
do
{
Sleep( 1 );
} while( TRUE );
}
void CALLBACK TimerProc(void* lpParameter,
BOOLEAN TimerOrWaitFired)
{
WORD wData;
UNREFERENCED_PARAMETER ( lpParameter );
UNREFERENCED_PARAMETER ( TimerOrWaitFired );
wData = gfpInp32( 0xA00 );
wData++;
gfpOut32( 0xA00, wData );
}
You can use SetThreadPriority to give priority to the critical thread. In this case, you'll probably need to create a thread explicitly and use CreateWaitableTimerEx, SetWaitableTimerEx, and WaitForSingleObjectEx instead of CreateTimerQueueTimer. Make sure the critical thread never spends too long executing between waits, or Windows may stop working properly.
This may not be enough, if the maximum lag is 100 microseconds. You might need to set your process priority class to REALTIME_PRIORITY_CLASS using the SetPriorityClass function, but make sure your program never holds the CPU for long or Windows will stop working properly. In particular, if your program hangs, the entire OS will hang; in this situation, there is no way to stop the program short of turning the power off.
Even this may not be enough. Windows is not a real-time operating system, and it may not be possible to get it do what you're asking for.
My experience with Windows and milli second is that it is not reliable.
I measured the Sleep api with an Oscilloscope via the Nusbio device.
And Sleep(0) is different from not calling the method at all.
Sleep(5) and Sleep(15) give inconsistent result sometime some time the wait is the same.
If you want this accuracy you need a micro controller, that can talk to your Windows application.
I have looked at the various topics relating to this, but couldn't find this specific issue I am having.
Things I looked at:
Injecting code into executable at runtime
C SIGSEGV Handler & Mprotect
Can I write-protect every page in the address space of a Linux process?
How to write a signal handler to catch SIGSEGV?
I am able to handle SIGSEGV gracefully when the protection needs to be set to either PROT_READ or PROT_WRITE in the handler. However, when I try to inject instructions with mmap, and then use mprotect to set it to PROT_READ only, and then I execute the instructions via inline assembly, it causes a SIGSEGV as intended, but the handler is unable to get the originating address causing the signal, so I am unable to mprotect it to PROT_READ | PROT_EXEC.
Example:
void sigHandler(int signum, siginfo_t *info, void *ptr) {
printf("Received signal number: %d\n", signum);
printf("Signal originates from process %lu\n",
(unsigned long)info->si_pid);
printf("SIGSEGV caused by this address: ? %p\n", info->si_addr);
char * alignedbaseAddr = (((unsigned int)(info->si_addr)) >> 12) * getPageSize();
printf("Aligning to %p\n", alignedbaseAddr);
//flip this page to be r+x
mprotect(alignedbaseAddr, getPageSize(), PROT_READ | PROT_EXEC);
}
void setupSignalHandler() {
action.sa_sigaction = sigHandler;
action.sa_flags = SA_SIGINFO;
sigemptyset(&action.sa_mask);
sigaction(SIGSEGV, &action, NULL);
}
int main(int argc, char *argv[]) {
char * baseAddr = (char*)mmap(NULL, getDiskSize(), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
if(baseAddr == MAP_FAILED) {
perror("Unable to mmap.");
}
printf("Process address space is %d\n", getDiskSize());
//no-op filler
for(int i = 0; i < (getDiskSize()) - 1; i++) {
baseAddr[i] = 0x90;
}
//ret instruction
baseAddr[i] = 0xc3;
if( mprotect(baseAddr, getDiskSize(), PROT_READ) == -1) {
perror("mprotect");
exit(1);
}
printf("Protecting addresses: %p to %p for READ_ONLY\n", baseAddr, baseAddr + getDiskSize() - 1);
setupSignalHandler();
__asm__
(
"call %%eax;"
: "=a" (output)
: "a" (baseAddr)
);
printf("Will this ever print?");
//close fd, and unmap memory
cleanUp();
return EXIT_SUCCESS;
}
Here is the resulting output:
Received signal number: 11
Signal originates from process 0
SIGSEGV caused by this address: ? (nil)
//the above output repeatedly loops, since it fails to "re mprotect" that page.
Architecture:
x86 32 bit
OS:
Ubuntu 11.04 - Linux version 2.6.38-12-generic (buildd#vernadsky) (gcc version 4.5.2 (Ubuntu/Linaro 4.5.2-8ubuntu4) )
Any ideas? The above logic works fine for simply read and writing into memory. Is there
a better way to execute instructions at runtime as opposed to inline assembly?
Thanks in advance!
In that case, the faulting address is the instruction pointer. Cast your third argument ptr (of your signal handler installed with SA_SIGINFO) to a ucontext_t, and retrieve the appropriate register, perhaps as (untested code!)
ucontext_t *uc = ptr;
void* faultyip = uc->uc_mcontext.gregs[REG_IP];
Read carefully /usr/include/sys/ucontext.h for more.
I'm interested to know why you are asking!!